How to Migrate from HP-UX to Linux: echo Command
You might think that migrating from HP-UX to Linux would be a piece of cake. Hey, they’re both UNIX, right? Sort of?
Naturally, it’s not that simple. Even among two UNIX-like environments, there are all sorts of pesky little differences to trip over. Typically the resulting problems are not hard to fix, but they can be hard to anticipate.
Lately we’ve been migrating an application from HP-UX to Red Hat Linux, and stumbling over a series of little gotchas. I plan to report some of them on this blog, and maybe save somebody else some hair-pulling.
For example: take the echo command.
Under HP-UX, echo recognizes escape sequences such as “\t” for horizonal tab, “\n” for newline, and so forth. Under Linux, it doesn’t, at least not by default. However the -e option tells the Linux version to recognize escape sequences.
One solution would be to look through all our shell scripts for ones that use echo with escape sequences, and fix them. Ideally, I should do that. However, the search would be tedious and time-consuming.
Instead, I defined the following alias in a logon script that everybody goes through:
alias echo=”echo -e”
If you really want echo not to recognize escape sequences, use the -E option, which works even with the alias in place. When the -e and -E options are both present, the last one wins.
Pedantic details:
Under HP-UX, the echo command is built into the shell, i.e. ksh and there is also a separate executable /usr/bin/echo. Both versions recognize escape sequences.
Likewise under Linux: the echo command is built into bash, and there is also a separate executable /bin/echo. Neither version recognizes escape sequences unless you include the -e option.
Building a List of Random Results Based on a Weighted Sort Index in T-SQL
I had an interesting requirement for a project recently. I needed to randomly sort database records that already have a sort preference number. That is to say, each record with the same sort number needs to be randomized in a group with others of the same number. Then those are returned as a group in an order based on the original sort order compared to a group of other sort numbers. Using this data for example:
|
ID |
Sort Pref |
|
1 |
10 |
|
2 |
10 |
|
3 |
200 |
|
4 |
200 |
|
5 |
200 |
|
6 |
333 |
|
7 |
333 |
I always want 1 and 2 to come before 3, 4, or 5 and for those before 6 and 7. But 1 and 2 could be in any order just like 3, 4, and 5 and so on. So either of these could be valid results: 1,2,5,3,4,7,6 or 2,1,4,3,5,6,7
I originally just returned them in an order of the SortPref padded with zeroes and appended with a NewID() guid. For example:
SELECT Right('0000000000' + Convert(varchar(10), SortPref), 10) + Convert(varchar(50), (NewID())) as SortPref
000000010EDE455E6-ED80-4752-9A26-3321226EDAA9
000000010B6D63097-9CBE-4D88-B43F-6CDEA460A028
000000200D02F7DDB-5245-42EF-A148-F8F34836DB1F
etc…
This worked, but one caveat is that I wanted the random order to be consistent, at least for a time. But every subsequent query returned a completely new order. For example, showing 3 per page, I could see 1,2,5. Then going to page 2 to see three more, I could see 3,5,7. That second batch was not the next three from the previous query. It is items 4-6 of a brand new query (notice 5 is in both). Then going back to page 1 will show 3 completely new random results in a different order, possibly 2, 1, 4.
Using the SQL Rand()function seemed like it was going to be great because passing it the same seed each time will produce the same “random” number and also consistent numbers each time thereafter. Each time the following SQL is executed it will return the same 3 numbers.
SELECT Rand(18), Rand(), Rand()
So I ditched the padding and guid and wanted to combine the existing sort preference number with a random decimal. I needed a new number for each row returned so I put the random number generating code right in the SELECT statement. This seems likely to work, but it does not. Rand() works similar to GetDate() in that the current datetime is fetched once and returned for every row. So I was getting the same suffix for each row.
SELECT SortPref + Rand (Cast (NewID () AS VarBinary)) AS SortPref
Since I need to get a new random number for each row, I instead made an update statement to put that result into a new integer column. This got me what I wanted and then I just sort by that column.
UPDATE List SET SortPref_RAND = SortPref + Rand( Cast( NewID() AS VarBinary ))
SELECT SortPref_RAND ORDER BY SortPref_RAND
|
ID |
Sort Pref |
Sort Pref with a Random Decimal |
|
2 |
10 |
10.0169181358024 |
|
1 |
10 |
10.8794841987447 |
|
5 |
200 |
200.296572565734 |
|
4 |
200 |
200.476788464425 |
|
3 |
200 |
200.579782703862 |
|
6 |
333 |
333.464425198756 |
|
7 |
333 |
333.782769181334 |
I chose to run this update daily so that a user’s results will not change even from the morning to evening. I keep track of the last date the random column was updated and if it is yesterday (so the first time a search is performed after midnight) then the update is performed again.
“T-SQL Debugging. Could not attach to SQL Server process” error
Problem:
When trying to start the debugger in SQL Server Management Studio, I received the error: Unable to start T-SQL Debugging. Could not attach to SQL Server process on ‘%dbservername%’. Click Help for more information.
Solution:
Configure the database engine service with a Domain user account, or more specifically, an account that can be authenticated from the machine that is running Management Studio. I noticed in a Wireshark trace on my pc that a NTLM call was being made with the account of the database engine service.
Unable to contact DPM protection agent Warnings in System Data Protection Manager
I was getting the following warning quite often from DPM (both 2007 and 2010 versions).
Status: Active
Computer: <computer>
Description: Unable to contact DPM protection agent.
The protection agent operation on <computer> failed because the service did not respond.
This was driving me crazy because everything looked to be running OK on both ends and it would eventually go away on its own. However one day right after receiving one of these warnings, I decided to log into the DPM server and see if it could see the problem computer. Sure enough, a ping failed. I also noticed that the ping command didn’t even return an IP address. Next I did a nslookup, which of course worked. So how can ping not find an IP address but nslookup can? I wish someone would enlighten me. However I know it has something to do with the DNS cache, and specifically the DNS Client service.
Restarting the DNS Client service made the ping work, and it also fixed the DPM warning. I got so annoyed by the warnings that I decided to disable the DNS Client service and I haven’t had any issues since…
Note I don’t believe this is a bug in DPM. In fact, since finding this I have also come across the same issue with Windows 7 and Windows Server 2008 (the DPM server is 2008 R2 btw). I have not been able to track down the source of the issue, but is seems like the DNS cache gets corrupted or something. I have even debated disabling this service on our SMB network, but I am afraid of the impact to our DNS server.
Create Computer Groups Based on 32-bit vs. 64-bit in System Center Essentials
Unfortunately System Center Essentials doesn’t come with computer groups that are based on whether or not Windows is installed as 32-bit or 64-bit. This would be extremely helpful in pushing software that is targeted for those specific platforms. Below is the management pack xml I came up with. You can save this XML as “Platform.Based.Computer.Groups.xml” and import via the console. It uses the PROCESSOR_ARCHITECTURE registry key to make the determination of a 32-bit vs. 64-bit OS. This creates 6 groups, 3 sets each split into x86 and x64: Windows <platform> Computer Group, Windows Client <platform> Computer Group, Windows Server <platform> Computer Group. To create the management pack by scratch, you can follow this outline:
- Create a new attribute for the HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE registry key value, targeting Windows Computer, Windows Client, and Windows Server. Yes this means you create 3 attributes.
- Create new groups for each platform. The rule for the x64 groups is the value of this key must equal “amd64”. The rule for the x86 groups is this key doesn’t equal “amd64”. More explanation can be found here (note the management agent/service runs native to the platform). For the Windows <platform> Group, make sure you use the Windows Computer_Extended class. For the Windows Client <platform> Computer Group, make sure you use the Windows Client_Extended class. For the Windows Server <platform> Computer Group, make sure you use the Windows Server_Extended class.
- Wait for the agents to set the new attribute.
Here is the Exported Management Pack. Note this was created using System Center Essentials 2010. I believe this would work under 2007, but different version numbers would need to be used.
<?xml version="1.0" encoding="utf-8"?><ManagementPack ContentReadable="true" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<Manifest>
<Identity>
<ID>Platform.Based.Computer.Groups</ID>
<Version>1.0.0.0</Version>
</Identity>
<Name>Platform Based Computer Groups</Name>
<References>
<Reference Alias="MicrosoftWindowsLibrary6172210">
<ID>Microsoft.Windows.Library</ID>
<Version>6.1.7221.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="MicrosoftSystemCenterInstanceGroupLibrary6172210">
<ID>Microsoft.SystemCenter.InstanceGroup.Library</ID>
<Version>6.1.7221.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="SystemCenter">
<ID>Microsoft.SystemCenter.Library</ID>
<Version>6.1.7221.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
</References>
</Manifest>
<TypeDefinitions>
<EntityTypes>
<ClassTypes>
<ClassType ID="Type79bcd4b047114bf38057cccfefc23b3f" Accessibility="Public" Abstract="false" Base="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Client.Computer" Hosted="false" Singleton="false">
<Property ID="AttributeDiscoveryGeneratedByUI8a18081aa8fd43f5b3b793fe2fd7d6db" Type="string" Key="false" CaseSensitive="false" Length="256" MinLength="0" />
</ClassType>
<ClassType ID="UINameSpacecb1cfa7fb7b44d699bba170cc1d1e5a8.Group" Accessibility="Public" Abstract="false" Base="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroup" Hosted="false" Singleton="true" />
<ClassType ID="UINameSpace9c461cdabc464754901456d880b76d42.Group" Accessibility="Public" Abstract="false" Base="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroup" Hosted="false" Singleton="true" />
<ClassType ID="Typec1ddf4898a8c45759b68eb55084f063d" Accessibility="Public" Abstract="false" Base="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Server.Computer" Hosted="false" Singleton="false">
<Property ID="AttributeDiscoveryGeneratedByUI770ab3335bf348469cad1fc8ffa25ba4" Type="string" Key="false" CaseSensitive="false" Length="256" MinLength="0" />
</ClassType>
<ClassType ID="Type2259d37e77334b7394a4bdb268a58764" Accessibility="Public" Abstract="false" Base="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer" Hosted="false" Singleton="false">
<Property ID="AttributeDiscoveryGeneratedByUI55895447f20b4390bc2657c1f92bd2b5" Type="string" Key="false" CaseSensitive="false" Length="256" MinLength="0" />
</ClassType>
<ClassType ID="UINameSpaced65a8b5eba8a497a817d94b078aa4764.Group" Accessibility="Public" Abstract="false" Base="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroup" Hosted="false" Singleton="true" />
<ClassType ID="UINameSpacece010ba3a104449096bd2cbbd8257088.Group" Accessibility="Public" Abstract="false" Base="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroup" Hosted="false" Singleton="true" />
<ClassType ID="UINameSpacef41b5a7897114ccbac3203997fd5f064.Group" Accessibility="Public" Abstract="false" Base="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroup" Hosted="false" Singleton="true" />
<ClassType ID="UINameSpaceb86ace359759416ca46f5aaa1ba33949.Group" Accessibility="Public" Abstract="false" Base="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroup" Hosted="false" Singleton="true" />
</ClassTypes>
</EntityTypes>
</TypeDefinitions>
<Monitoring>
<Discoveries>
<Discovery ID="AttributeDiscoveryGeneratedByUIcf48023b73e54e8dae3405dd1ff63ae4" Enabled="true" Target="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Client.Computer" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>PerformanceCollection</Category>
<DiscoveryTypes>
<DiscoveryClass TypeID="Type79bcd4b047114bf38057cccfefc23b3f">
<Property TypeID="Type79bcd4b047114bf38057cccfefc23b3f" PropertyID="AttributeDiscoveryGeneratedByUI8a18081aa8fd43f5b3b793fe2fd7d6db" />
</DiscoveryClass>
</DiscoveryTypes>
<DataSource ID="AttributeDiscoveryGeneratedByUI538c41746aa249058ff191fc55335053" TypeID="MicrosoftWindowsLibrary6172210!Microsoft.Windows.RegistryDiscoverySingleProvider">
<ComputerName>$Target/Property[Type="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/NetworkName$</ComputerName>
<AttributeName>AttributeDiscoveryRule7a8459cae84842f082b2f7da5b2fa27a</AttributeName>
<Path>SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE</Path>
<PathType>1</PathType>
<AttributeType>1</AttributeType>
<Frequency>3600</Frequency>
<ClassId>$MPElement[Name="Type79bcd4b047114bf38057cccfefc23b3f"]$</ClassId>
<InstanceSettings>
<Settings>
<Setting>
<Name>$MPElement[Name="Type79bcd4b047114bf38057cccfefc23b3f"]/AttributeDiscoveryGeneratedByUI8a18081aa8fd43f5b3b793fe2fd7d6db$</Name>
<Value>$Data/Values/AttributeDiscoveryRule7a8459cae84842f082b2f7da5b2fa27a$</Value>
</Setting>
<Setting>
<Name>$MPElement[Name="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/PrincipalName$</Name>
<Value>$Target/Property[Type="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/PrincipalName$</Value>
</Setting>
</Settings>
</InstanceSettings>
</DataSource>
</Discovery>
<Discovery ID="UINameSpacecb1cfa7fb7b44d699bba170cc1d1e5a8.Group.DiscoveryRule" Enabled="true" Target="UINameSpacecb1cfa7fb7b44d699bba170cc1d1e5a8.Group" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>Discovery</Category>
<DiscoveryTypes>
<DiscoveryRelationship TypeID="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities" />
</DiscoveryTypes>
<DataSource ID="GroupPopulationDataSource" TypeID="SystemCenter!Microsoft.SystemCenter.GroupPopulator">
<RuleId>$MPElement$</RuleId>
<GroupInstanceId>$MPElement[Name="UINameSpacecb1cfa7fb7b44d699bba170cc1d1e5a8.Group"]$</GroupInstanceId>
<MembershipRules>
<MembershipRule>
<MonitoringClass>$MPElement[Name="Type79bcd4b047114bf38057cccfefc23b3f"]$</MonitoringClass>
<RelationshipClass>$MPElement[Name="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities"]$</RelationshipClass>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property>$MPElement[Name="Type79bcd4b047114bf38057cccfefc23b3f"]/AttributeDiscoveryGeneratedByUI8a18081aa8fd43f5b3b793fe2fd7d6db$</Property>
</ValueExpression>
<Operator>NotEqual</Operator>
<ValueExpression>
<Value>amd64</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</MembershipRule>
</MembershipRules>
</DataSource>
</Discovery>
<Discovery ID="UINameSpace9c461cdabc464754901456d880b76d42.Group.DiscoveryRule" Enabled="true" Target="UINameSpace9c461cdabc464754901456d880b76d42.Group" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>Discovery</Category>
<DiscoveryTypes>
<DiscoveryRelationship TypeID="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities" />
</DiscoveryTypes>
<DataSource ID="GroupPopulationDataSource" TypeID="SystemCenter!Microsoft.SystemCenter.GroupPopulator">
<RuleId>$MPElement$</RuleId>
<GroupInstanceId>$MPElement[Name="UINameSpace9c461cdabc464754901456d880b76d42.Group"]$</GroupInstanceId>
<MembershipRules>
<MembershipRule>
<MonitoringClass>$MPElement[Name="Type79bcd4b047114bf38057cccfefc23b3f"]$</MonitoringClass>
<RelationshipClass>$MPElement[Name="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities"]$</RelationshipClass>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property>$MPElement[Name="Type79bcd4b047114bf38057cccfefc23b3f"]/AttributeDiscoveryGeneratedByUI8a18081aa8fd43f5b3b793fe2fd7d6db$</Property>
</ValueExpression>
<Operator>Equal</Operator>
<ValueExpression>
<Value>amd64</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</MembershipRule>
</MembershipRules>
</DataSource>
</Discovery>
<Discovery ID="AttributeDiscoveryGeneratedByUIc35946fd1e9246bb91ff701b971134c9" Enabled="true" Target="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Server.Computer" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>PerformanceCollection</Category>
<DiscoveryTypes>
<DiscoveryClass TypeID="Typec1ddf4898a8c45759b68eb55084f063d">
<Property TypeID="Typec1ddf4898a8c45759b68eb55084f063d" PropertyID="AttributeDiscoveryGeneratedByUI770ab3335bf348469cad1fc8ffa25ba4" />
</DiscoveryClass>
</DiscoveryTypes>
<DataSource ID="AttributeDiscoveryGeneratedByUI553f00ed2fbd4b4d8bf516bad763fa75" TypeID="MicrosoftWindowsLibrary6172210!Microsoft.Windows.RegistryDiscoverySingleProvider">
<ComputerName>$Target/Property[Type="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/NetworkName$</ComputerName>
<AttributeName>AttributeDiscoveryRulec017456d384b4bb9860dac5b91dcf8c2</AttributeName>
<Path>SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE</Path>
<PathType>1</PathType>
<AttributeType>1</AttributeType>
<Frequency>3600</Frequency>
<ClassId>$MPElement[Name="Typec1ddf4898a8c45759b68eb55084f063d"]$</ClassId>
<InstanceSettings>
<Settings>
<Setting>
<Name>$MPElement[Name="Typec1ddf4898a8c45759b68eb55084f063d"]/AttributeDiscoveryGeneratedByUI770ab3335bf348469cad1fc8ffa25ba4$</Name>
<Value>$Data/Values/AttributeDiscoveryRulec017456d384b4bb9860dac5b91dcf8c2$</Value>
</Setting>
<Setting>
<Name>$MPElement[Name="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/PrincipalName$</Name>
<Value>$Target/Property[Type="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/PrincipalName$</Value>
</Setting>
</Settings>
</InstanceSettings>
</DataSource>
</Discovery>
<Discovery ID="AttributeDiscoveryGeneratedByUI4fcdb3368e174252a02253a63dc5373b" Enabled="true" Target="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>PerformanceCollection</Category>
<DiscoveryTypes>
<DiscoveryClass TypeID="Type2259d37e77334b7394a4bdb268a58764">
<Property TypeID="Type2259d37e77334b7394a4bdb268a58764" PropertyID="AttributeDiscoveryGeneratedByUI55895447f20b4390bc2657c1f92bd2b5" />
</DiscoveryClass>
</DiscoveryTypes>
<DataSource ID="AttributeDiscoveryGeneratedByUI2cc5aaef5b8c4e849fe5af1833a0115f" TypeID="MicrosoftWindowsLibrary6172210!Microsoft.Windows.RegistryDiscoverySingleProvider">
<ComputerName>$Target/Property[Type="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/NetworkName$</ComputerName>
<AttributeName>AttributeDiscoveryRule95424e49ca10467eb12d4611633759c5</AttributeName>
<Path>SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE</Path>
<PathType>1</PathType>
<AttributeType>1</AttributeType>
<Frequency>3600</Frequency>
<ClassId>$MPElement[Name="Type2259d37e77334b7394a4bdb268a58764"]$</ClassId>
<InstanceSettings>
<Settings>
<Setting>
<Name>$MPElement[Name="Type2259d37e77334b7394a4bdb268a58764"]/AttributeDiscoveryGeneratedByUI55895447f20b4390bc2657c1f92bd2b5$</Name>
<Value>$Data/Values/AttributeDiscoveryRule95424e49ca10467eb12d4611633759c5$</Value>
</Setting>
<Setting>
<Name>$MPElement[Name="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/PrincipalName$</Name>
<Value>$Target/Property[Type="MicrosoftWindowsLibrary6172210!Microsoft.Windows.Computer"]/PrincipalName$</Value>
</Setting>
</Settings>
</InstanceSettings>
</DataSource>
</Discovery>
<Discovery ID="UINameSpaced65a8b5eba8a497a817d94b078aa4764.Group.DiscoveryRule" Enabled="true" Target="UINameSpaced65a8b5eba8a497a817d94b078aa4764.Group" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>Discovery</Category>
<DiscoveryTypes>
<DiscoveryRelationship TypeID="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities" />
</DiscoveryTypes>
<DataSource ID="GroupPopulationDataSource" TypeID="SystemCenter!Microsoft.SystemCenter.GroupPopulator">
<RuleId>$MPElement$</RuleId>
<GroupInstanceId>$MPElement[Name="UINameSpaced65a8b5eba8a497a817d94b078aa4764.Group"]$</GroupInstanceId>
<MembershipRules>
<MembershipRule>
<MonitoringClass>$MPElement[Name="Typec1ddf4898a8c45759b68eb55084f063d"]$</MonitoringClass>
<RelationshipClass>$MPElement[Name="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities"]$</RelationshipClass>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property>$MPElement[Name="Typec1ddf4898a8c45759b68eb55084f063d"]/AttributeDiscoveryGeneratedByUI770ab3335bf348469cad1fc8ffa25ba4$</Property>
</ValueExpression>
<Operator>NotEqual</Operator>
<ValueExpression>
<Value>amd64</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</MembershipRule>
</MembershipRules>
</DataSource>
</Discovery>
<Discovery ID="UINameSpacece010ba3a104449096bd2cbbd8257088.Group.DiscoveryRule" Enabled="true" Target="UINameSpacece010ba3a104449096bd2cbbd8257088.Group" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>Discovery</Category>
<DiscoveryTypes>
<DiscoveryRelationship TypeID="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities" />
</DiscoveryTypes>
<DataSource ID="GroupPopulationDataSource" TypeID="SystemCenter!Microsoft.SystemCenter.GroupPopulator">
<RuleId>$MPElement$</RuleId>
<GroupInstanceId>$MPElement[Name="UINameSpacece010ba3a104449096bd2cbbd8257088.Group"]$</GroupInstanceId>
<MembershipRules>
<MembershipRule>
<MonitoringClass>$MPElement[Name="Typec1ddf4898a8c45759b68eb55084f063d"]$</MonitoringClass>
<RelationshipClass>$MPElement[Name="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities"]$</RelationshipClass>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property>$MPElement[Name="Typec1ddf4898a8c45759b68eb55084f063d"]/AttributeDiscoveryGeneratedByUI770ab3335bf348469cad1fc8ffa25ba4$</Property>
</ValueExpression>
<Operator>Equal</Operator>
<ValueExpression>
<Value>amd64</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</MembershipRule>
</MembershipRules>
</DataSource>
</Discovery>
<Discovery ID="UINameSpacef41b5a7897114ccbac3203997fd5f064.Group.DiscoveryRule" Enabled="true" Target="UINameSpacef41b5a7897114ccbac3203997fd5f064.Group" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>Discovery</Category>
<DiscoveryTypes>
<DiscoveryRelationship TypeID="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities" />
</DiscoveryTypes>
<DataSource ID="GroupPopulationDataSource" TypeID="SystemCenter!Microsoft.SystemCenter.GroupPopulator">
<RuleId>$MPElement$</RuleId>
<GroupInstanceId>$MPElement[Name="UINameSpacef41b5a7897114ccbac3203997fd5f064.Group"]$</GroupInstanceId>
<MembershipRules>
<MembershipRule>
<MonitoringClass>$MPElement[Name="Type2259d37e77334b7394a4bdb268a58764"]$</MonitoringClass>
<RelationshipClass>$MPElement[Name="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities"]$</RelationshipClass>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property>$MPElement[Name="Type2259d37e77334b7394a4bdb268a58764"]/AttributeDiscoveryGeneratedByUI55895447f20b4390bc2657c1f92bd2b5$</Property>
</ValueExpression>
<Operator>NotEqual</Operator>
<ValueExpression>
<Value>amd64</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</MembershipRule>
</MembershipRules>
</DataSource>
</Discovery>
<Discovery ID="UINameSpaceb86ace359759416ca46f5aaa1ba33949.Group.DiscoveryRule" Enabled="true" Target="UINameSpaceb86ace359759416ca46f5aaa1ba33949.Group" ConfirmDelivery="false" Remotable="true" Priority="Normal">
<Category>Discovery</Category>
<DiscoveryTypes>
<DiscoveryRelationship TypeID="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities" />
</DiscoveryTypes>
<DataSource ID="GroupPopulationDataSource" TypeID="SystemCenter!Microsoft.SystemCenter.GroupPopulator">
<RuleId>$MPElement$</RuleId>
<GroupInstanceId>$MPElement[Name="UINameSpaceb86ace359759416ca46f5aaa1ba33949.Group"]$</GroupInstanceId>
<MembershipRules>
<MembershipRule>
<MonitoringClass>$MPElement[Name="Type2259d37e77334b7394a4bdb268a58764"]$</MonitoringClass>
<RelationshipClass>$MPElement[Name="MicrosoftSystemCenterInstanceGroupLibrary6172210!Microsoft.SystemCenter.InstanceGroupContainsEntities"]$</RelationshipClass>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property>$MPElement[Name="Type2259d37e77334b7394a4bdb268a58764"]/AttributeDiscoveryGeneratedByUI55895447f20b4390bc2657c1f92bd2b5$</Property>
</ValueExpression>
<Operator>Equal</Operator>
<ValueExpression>
<Value>amd64</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</MembershipRule>
</MembershipRules>
</DataSource>
</Discovery>
</Discoveries>
</Monitoring>
<Presentation>
<Folders>
<Folder ID="Folder_3a3150e06af04efc93e10ce2cbdb67a5" Accessibility="Public" ParentFolder="SystemCenter!Microsoft.SystemCenter.Monitoring.ViewFolder.Root" />
</Folders>
</Presentation>
<LanguagePacks>
<LanguagePack ID="ENU" IsDefault="false">
<DisplayStrings>
<DisplayString ElementID="Platform.Based.Computer.Groups">
<Name>Platform Based Computer Groups</Name>
</DisplayString>
<DisplayString ElementID="Folder_3a3150e06af04efc93e10ce2cbdb67a5">
<Name>Platform Based Computer Groups</Name>
</DisplayString>
<DisplayString ElementID="AttributeDiscoveryGeneratedByUIcf48023b73e54e8dae3405dd1ff63ae4">
<Name>Process ArchitectureDiscovery</Name>
</DisplayString>
<DisplayString ElementID="Type79bcd4b047114bf38057cccfefc23b3f">
<Name>Windows Client_Extended</Name>
</DisplayString>
<DisplayString ElementID="Type79bcd4b047114bf38057cccfefc23b3f" SubElementID="AttributeDiscoveryGeneratedByUI8a18081aa8fd43f5b3b793fe2fd7d6db">
<Name>Process Architecture</Name>
<Description>Determines 32-bit or 64-bit version of windows based on the HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE</Description>
</DisplayString>
<DisplayString ElementID="UINameSpacecb1cfa7fb7b44d699bba170cc1d1e5a8.Group">
<Name>Windows Client x86 Computer Group</Name>
</DisplayString>
<DisplayString ElementID="UINameSpacecb1cfa7fb7b44d699bba170cc1d1e5a8.Group.DiscoveryRule">
<Name>Populate Windows Client x86 Computer Group</Name>
<Description>This discovery rule populates the group ‘Windows Client x86 Computer Group’</Description>
</DisplayString>
<DisplayString ElementID="UINameSpace9c461cdabc464754901456d880b76d42.Group">
<Name>Windows Client x64 Computer Group</Name>
</DisplayString>
<DisplayString ElementID="UINameSpace9c461cdabc464754901456d880b76d42.Group.DiscoveryRule">
<Name>Populate Windows Client x64 Computer Group</Name>
<Description>This discovery rule populates the group ‘Windows Client x64 Computer Group’</Description>
</DisplayString>
<DisplayString ElementID="AttributeDiscoveryGeneratedByUIc35946fd1e9246bb91ff701b971134c9">
<Name>Process ArchitectureDiscovery</Name>
</DisplayString>
<DisplayString ElementID="Typec1ddf4898a8c45759b68eb55084f063d">
<Name>Windows Server_Extended</Name>
</DisplayString>
<DisplayString ElementID="Typec1ddf4898a8c45759b68eb55084f063d" SubElementID="AttributeDiscoveryGeneratedByUI770ab3335bf348469cad1fc8ffa25ba4">
<Name>Process Architecture</Name>
<Description>Determines 32-bit or 64-bit version of windows based on the HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE</Description>
</DisplayString>
<DisplayString ElementID="AttributeDiscoveryGeneratedByUI4fcdb3368e174252a02253a63dc5373b">
<Name>Process ArchitectureDiscovery</Name>
</DisplayString>
<DisplayString ElementID="Type2259d37e77334b7394a4bdb268a58764">
<Name>Windows Computer_Extended</Name>
</DisplayString>
<DisplayString ElementID="Type2259d37e77334b7394a4bdb268a58764" SubElementID="AttributeDiscoveryGeneratedByUI55895447f20b4390bc2657c1f92bd2b5">
<Name>Process Architecture</Name>
<Description>Determines 32-bit or 64-bit version of windows based on the HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment\PROCESSOR_ARCHITECTURE</Description>
</DisplayString>
<DisplayString ElementID="UINameSpaced65a8b5eba8a497a817d94b078aa4764.Group">
<Name>Windows Server x86 Computer Group</Name>
<Description />
</DisplayString>
<DisplayString ElementID="UINameSpaced65a8b5eba8a497a817d94b078aa4764.Group.DiscoveryRule">
<Name>Populate Windows Server x86 Computer Group</Name>
<Description>This discovery rule populates the group ‘Windows Server x86 Computer Group’</Description>
</DisplayString>
<DisplayString ElementID="UINameSpacece010ba3a104449096bd2cbbd8257088.Group">
<Name>Windows Server x64 Computer Group</Name>
</DisplayString>
<DisplayString ElementID="UINameSpacece010ba3a104449096bd2cbbd8257088.Group.DiscoveryRule">
<Name>Populate Windows Server x64 Computer Group</Name>
<Description>This discovery rule populates the group ‘Windows Server x64 Computer Group’</Description>
</DisplayString>
<DisplayString ElementID="UINameSpacef41b5a7897114ccbac3203997fd5f064.Group">
<Name>Windows x86 Computer Group</Name>
</DisplayString>
<DisplayString ElementID="UINameSpacef41b5a7897114ccbac3203997fd5f064.Group.DiscoveryRule">
<Name>Populate Windows x86 Computer Group</Name>
<Description>This discovery rule populates the group ‘Windows x86 Computer Group’</Description>
</DisplayString>
<DisplayString ElementID="UINameSpaceb86ace359759416ca46f5aaa1ba33949.Group">
<Name>Windows x64 Computer Group</Name>
</DisplayString>
<DisplayString ElementID="UINameSpaceb86ace359759416ca46f5aaa1ba33949.Group.DiscoveryRule">
<Name>Populate Windows x64 Computer Group</Name>
<Description>This discovery rule populates the group ‘Windows x64 Computer Group’</Description>
</DisplayString>
</DisplayStrings>
</LanguagePack>
</LanguagePacks>
</ManagementPack>
Selecting An Old Value While Binding a DropDownList
I had a usual instance where a DropDownList was bound to a table in a database. However, that list of data could change in the database without regard to those values having been previously stored (as text, not IDs, unfortunately) in another table. Meaning that when the DropDownList would now be loaded with the newly updated data, the previously selected value would not have a corresponding choice in the drop down anymore.
The DropDownList doesn’t take too kindly to this and gives an ArgumentOutOfRangeException error. But I needed that old value as a possible choice in the dropdown still, as well as the new choices.
The problem was that I needed to get the saved value from the database (which failed to be the initial SelectedValue). So I just stored it in the ToolTip for the DropDownList, then I could retrieve it and update it from anywhere.
Note: Be sure to use OnDataBinding not OnDataBound to add the new item.
<asp:DropDownList ID=”HotelNameDropDown” runat=”Server” DataSourceID=”ObjectDataSource1″
SelectedValue=’<%# Bind(“HotelName”) %>‘ AppendDataBoundItems=”true”
OnDataBinding=”HotelNameDropDown_OnDataBinding” ToolTip=’<%# Bind(“HotelName”) %>‘
OnSelectedIndexChanged=”HotelNameDropDown_OnSelectedIndexChanged”
DataTextField=”HotelName” DataValueField=”HotelName” />
Depending on when you postback, you might also need to update the ToolTip when the user changes the DropDownList.
protected void HotelNameDropDown_OnSelectedIndexChanged(object sender, EventArgs e)
{
// Set the tooltip to the selected value onchange, becuase we will use the tooltip below
DropDownList ddl = (DropDownList)sender;
ddl.ToolTip = ddl.SelectedValue;
}
Here I try to bind the DropDownList with the data, if this fails then it creates a new ListItem at the top of the list with a name and value of what we had stored in the ToolTip from the .aspx page.
protected void HotelNameDropDown_OnDataBinding(object sender, EventArgs e)
{
DropDownList ddl = (DropDownList)sender;
ddl.DataBinding -= new EventHandler(HotelNameDropDown_OnDataBinding);
try
{
ddl.AppendDataBoundItems = false;
ddl.DataBind();
ddl.SelectedValue = ddl.ToolTip;
}
catch(ArgumentOutOfRangeException)
{
ddl.Items.Clear();
ddl.AppendDataBoundItems = true;
ListItem li = new ListItem(ddl.ToolTip, ddl.ToolTip);
li.Selected = true;
ddl.Items.Insert(0, li);
}
}
More info about this topic can be found here:
Dynamically Loading External Controls from a DropDownList
Displaying a specific web user control (.ascx) from a dropdown selection is a fairly straightforward process.
Create an asp:DropDownList with OnSelectedIndexChanged set to a function. This function will load a user control file based on the selected value of the dropdown. Also, create an asp:PlaceHolder where the control will be placed.
<asp:DropDownList ID=”ddDataTables” runat=”server” AutoPostBack=”true”
OnSelectedIndexChanged=”ddDataTables_Changed” >
<asp:ListItem Text=”" Value=”"></asp:ListItem>
<asp:ListItem Text=”More Options” Value=”more_options”></asp:ListItem>
<asp:ListItem Text=”Address” Value=”address”></asp:ListItem>
…
<asp:PlaceHolder ID=”phDataTable” EnableViewState=”false” runat=”server” />
And the code behind file looks for a file which is named the same as the selected value (e.g. address.ascx), then adds it to the place holder in the aspx file.
protected void ddDataTables_Changed(object sender, EventArgs e)
{
LoadUserControl(ddDataTables.SelectedValue);
}
protected void LoadUserControl(string strSelectedTable)
{
phDataTable.Controls.Clear();
if (strSelectedTable != “”)
{
UserControl ucDataTable = (UserControl)LoadControl(strSelectedTable + “.ascx”);
phDataTable.Controls.Add(ucDataTable);
}
}
That’s it. A simple way to keep functionality separated in web user controls but be able to still pull them in cleanly when desired.
Triggering a Specific GridView Row Command When Page Loads
I have an asp.net page with a gridview and each row uses a TemplateField to make a LinkButton to select the row. In my case, the action of clicking the text link triggers a FormView to appear in order to edit the data.
I needed a way to open the editing form automatically for the first item in the gridview when the page loads. After using combinations of different .NET page events (Page_Render(), Page_Unload(), etc.), I found myself going around and around because I was never at the right point in the execution order for getting the data bound , knowing the correct CommandArgument and having access to all the data in the row at the same time. I was setting session variables and checking IsPostBack and it was becoming more complicated than it seemed like it needed to be.
It was time to rethink the whole issue. I ended up writing 1 line of javascript with a little prep C# code which finds the correct LinkButton, transforms its .NET generated ID into something useful, and then stores it for the javascript to use. The javascript executes a postback after the page loads so it mimics a user clicking on the “Edit” link, just like I wanted.
The code for the edit link as a column in my gridview:
<asp:TemplateField ShowHeader=”False”>
<ItemTemplate>
<asp:LinkButton ID=”LinkButtonSelect” runat=”server” CausesValidation=”False”
CommandName=”Select” Text=”EDIT”
CommandArgument=’<%# Bind(“ID”)%>‘>
</asp:LinkButton>
</ItemTemplate>
</asp:TemplateField>
In my C# code I check if there are any rows in my grid before I attempt to postback on anything and I’m choosing row 0 because I want the first row. The parameter for __doPostBack needs to have dollar signs instead of underscores like the ID has, so I replace them accordingly.
At the bottom of my.aspx page I have this javascript code (which could also be added into the onload event):
<script type=”text/javascript”>
<%
// Get and format the the ID of the Edit link in the first row
if (GridView1.Rows.Count > 0)
{
LinkButton lnkEdit = (LinkButton)GridView1.Rows[0].FindControl(“LinkButtonSelect”);
string strEditID = lnkEdit.ClientID.ToString().Replace(“_”,“$”);
%>
// trigger a postback like someone clicked “Edit”
__doPostBack(‘<%= strEditID %>’, ”);
<%
}
%>
</script>
So in the end, the javascript line has the same value as the href attribute that is generated for the LinkButton. View the source code of your page and check it out!
Display a Nested List Inside Another Repeater
A simple way to display a list of data is to use an asp:Repeater. If the data also needs to show a nested list of related data for each main item, one can place another Repeater inside the first. In the code behind, the queries used for each Repeater can be linked in a dataset as a parent-child relationship via a Data Relation.
In the example below we make the multiple queries in only one SQL command statement, then link the result tables together by making a new DataRelation. The link uses key and foreign key ID columns from each result set.
This C# example shows how you can have a list of phone numbers as an area inside a larger list of contacts.
In the Page_Load function…
…
// Create and fill a DataSet
SqlDataAdapter myCommand = new SqlDataAdapter(
"SELECT DISTINCT MemberID, Address, FirstName, LastName " +
" FROM MemberNames M; " +
"SELECT MemID, phonetype, Number " +
" FROM MemberNames M " +
" INNER JOIN Phone P ON M.MemberID = P.MemID;" +
, myConnection);
DataSet ds = new DataSet();
myCommand.Fill(ds);
// Relate the two tables from the query together
ds.Relations.Add(new DataRelation("MemberID_Phone", ds.Tables[0].Columns["MemberID"], ds.Tables[1].Columns["MemID"]));
// Bind the outer Repeater to the DataSet.
rptMember.DataSource = ds.Tables[0];
rptMember.DataBind();
When we bind the data for each item in the outer Repeater, we will create a child view using the relation we linked previously.
protected void rptMember_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
DataRowView drv = e.Item.DataItem as DataRowView;
Repeater rptPhone = e.Item.FindControl("rptPhone") as Repeater;
rptPhone.DataSource = drv.CreateChildView("MemberID_Phone");
rptPhone.DataBind();
}
This snippet from the .aspx files shows the nested repeaters.
<asp:Repeater id="rptMember" OnItemDataBound="rptMember_ItemDataBound" runat="server">
<ItemTemplate>
<!– Tags to display the bound data (name, address, etc.) –>
<!– Make a repeater for all phone numbers for each person –>
<asp:Repeater id="rptPhone" runat="server">
<ItemTemplate>
<%# DataBinder.Eval(Container.DataItem, "PhoneType")%>:
<%# DataBinder.Eval(Container.DataItem, "Number")%>
</ItemTemplate>
</asp:Repeater>
…
To sum it all up, we implemented several technical elements here.
- Nested Repeaters
- Using a multi-result query
- Using DataSet Relations
Our example displays a list of Contacts with a sub-list for multiple phone numbers.
Article Series and Planned Topics
by Allan Sieker
When it comes time to write an interesting article about a technical topic my mind goes into a deadlock in trying to find the balance between space/time constraints and keeping the content interesting. Too short of an article and it seems trivial because the technical stuff doesn’t get covered enough. Too technical, and the article becomes long and boring. All the while, wanting to keep things original, informative, and light. So did I end up with? How about a series of related articles that covers something that is near and dear to all of us?
I bought my first computer in 1978 (yes, I still have it) and as my home network expanded to what it is now – several servers, workstations, and laptops, the need for keeping a file inventory goes with the territory. Sure, over the years I created my own file databases written in several languages (BASIC, Pascal, dBASE, Clipper, VB, C#) and they all served their purpose, but technology keeps improving and I always want more.
What if data warehousing concepts were applied to capture the “slowly changing dimension” of file updates? What if file collections were recognized and managed as applications and other entities? What if all of the computer file inventories were gathered locally then stored centrally for searches via a web interface? What if backup history were also available?
This article series will cover a broad range of technical topics with the end goal being a respectable system for home or business usage. Concepts will be discussed and code will be available for download. References to other articles and postings will also be made.
Here is a brief list of planned topics:
- Using recursive methods to collect file information from all of the folders on a drive.
- Creating console and Windows “file agent” applications to collect file data and write to an XML file.
- Creating a SQL Server file inventory database.
- Balancing cost and architecture to avoid over-costing and over-engineering.
- Importing “file agent” XML into the database.
- Creating an ASP.NET web application for searching and retrieving application & file information.
- Making “file agent” applications downloadable from the web site using ClickOnce.
- Using the Visual Studio Report Designer and the ReportViewer control to create web reports.
- Creating a “wrapper” application for Microsoft’s Backup to manage and track backups.
- Detecting media and image file duplicates based on file content instead of file name.
Feedback is always welcome.