Friday, May 22, 2009

A valued member of the Tea Party Nation, Dr. G, has a blog post on his site that everyone should read. It is absolutely amazing that this type of action can go on in any nation that considers itself to be of first-world caliber, and it disturbs me greatly that nobody did anything about it.

It reminds me of a poem called "First they came...", often attributed to Pastor Martin Niemöller, and one with which many are familiar in some form or another. It is transcribed below:
When the Nazis came for the communists,
I remained silent;
I was not a communist.

Then they locked up the social democrats,
I remained silent;
I was not a social democrat.

Then they came for the trade unionists,
I did not protest;
I was not a trade unionist.

Then they came for the Jews,
I did not speak out;
I was not a Jew.

When they came for me,
there was no one left to speak out for me.
Folks, we have to start standing up for what we believe and stop being the silent majority. We have to begin to challenge those that would seek to undermine the Judeo-Christian principles on which our country was founded. We have to take to task those that preach of tolerance and equity in all facets of life except for Christianity. We should not forget the instructions provided to us by the Holy Bible, which tells us:
Revelation 3:16 (NLT): But since you are like lukewarm water, neither hot nor cold, I will spit you out of my mouth!

James 1:6-8 (NLT): 6But when you ask him, be sure that your faith is in God alone. Do not waver, for a person with divided loyalty is as unsettled as a wave of the sea that is blown and tossed by the wind. 7Such people should not expect to receive anything from the Lord. 8Their loyalty is divided between God and the world, and they are unstable in everything they do.
I'm concerned that we're becoming lukewarm. We see and tolerate things every single day that are detestable to our Father in Heaven. That worries me, because our sin (and our tolerance of sin) is what keeps us from entering into the glory of a relationship with our Creator. Hebrews 10:26-39 (NLT) simultaneously fascinates and convicts me, as it speaks not only to God's undying love for us and the boundless rewards that can be expected by those that do His will, but also of the judgment that awaits people that fail to do His work (emphasis mine):
26Dear friends, if we deliberately continue sinning after we have received knowledge of the truth, there is no longer any sacrifice that will cover these sins. 27There is only the terrible expectation of God’s judgment and the raging fire that will consume his enemies. 28For anyone who refused to obey the law of Moses was put to death without mercy on the testimony of two or three witnesses. 29Just think how much worse the punishment will be for those who have trampled on the Son of God, and have treated the blood of the covenant, which made us holy, as if it were common and unholy, and have insulted and disdained the Holy Spirit who brings God’s mercy to us. 30For we know the one who said,

“I will take revenge.
I will pay them back.”

He also said,

“The Lord will judge his own people.”

31It is a terrible thing to fall into the hands of the living God.

32Think back on those early days when you first learned about Christ. Remember how you remained faithful even though it meant terrible suffering. 33Sometimes you were exposed to public ridicule and were beaten, and sometimes you helped others who were suffering the same things. 34You suffered along with those who were thrown into jail, and when all you owned was taken from you, you accepted it with joy. You knew there were better things waiting for you that will last forever.

35So do not throw away this confident trust in the Lord. Remember the great reward it brings you! 36Patient endurance is what you need now, so that you will continue to do God’s will. Then you will receive all that he has promised.

37“For in just a little while,
the Coming One will come and not delay.
38And my righteous ones will live by faith.
But I will take no pleasure in anyone who turns away.”

39But we are not like those who turn away from God to their own destruction. We are the faithful ones, whose souls will be saved.
Sometimes I feel like it's a losing battle trying to stem the tide against us. Sometimes I want to give up. I know where those feeling come from, however...the Devil is clever in how he tries to weaken us in an effort to break us down. I know that because fear is not a fruit of the spirit.

We have to put on the whole armor of God, and stand.

Friday, January 16, 2009

Dynamic list of years in T-SQL

I have many SQL Server 2005 Reporting Services reports that include a year value as a parameter. Recently I was asked to make this more dynamic, allowing for a rolling list of years from which the user can select.

Here is the table function I created, which I think should only work in SQL Server 2005 and up because of the parametrized TOP value:
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE FUNCTION dbo.udtf_GetDynamicYearList
(
    @StartYear INT -- The first year you want in the list
    , @NumberofYears INT -- The total number of years you want (from the Start Year)
)
RETURNS TABLE
AS
RETURN
(
    SELECT
        TOP (@NumberofYears) *
    FROM
    (
        SELECT
            @StartYear + n1.num AS [Year]
        FROM
        (
            SELECT 0 AS num UNION ALL
            SELECT 1 UNION ALL
            SELECT 2 UNION ALL
            SELECT 3 UNION ALL
            SELECT 4 UNION ALL
            SELECT 5 UNION ALL
            SELECT 6 UNION ALL
            SELECT 7 UNION ALL
            SELECT 8 UNION ALL
            SELECT 9
        ) n1
    ) GenCalendar
    ORDER BY 1
)
GO
Simple! Now you can call it like so:
SELECT * FROM dbo.udtf_GetDynamicYearList(2006, 10)
If you want it to be more dynamic (say, to start from last year), you can do:
SELECT * FROM dbo.udtf_GetDynamicYearList(YEAR(GETDATE())-1, 10)

ODBC Connection to Informix 7.2 Server

I recently had to figure out a way to connect remotely to an Informix 7.2 server running on AIX 4. After struggling a bit, I finally got it working. I thought a checklist might be useful on the off chance that someone else has to do something similar.

Prepare the Informix instance for remote connectivity

Step 1: Ensure that an entry for the network-enabled version of the Informix instance exists in $INFORMIXDIR/etc/sqlhosts. Mine reads:
tcpipserver onsoctcp rs6000 on_socket
Entries in this file are in the following format :
[Database instance alias] [Protocol name] [Host name] [TCP service name]
Step 2: Add the database instance alias name to the list of server names in your onconfig file. This is found in the $INFORMIXDIR/etc directory as well - its extension is often the name of your database. Find the DBSERVERALIASES line, and (in our example) set its value to tcpipserver. If this key already contains a value, you can add tcpipserver to the list (and up to 32 total) by separating the aliases with commas.

Step 3: Edit your /etc/services file to include a service name and port for remote connections. The most common port to use is 1526/tcp. In our example, we'd add:
on_socket 1526/tcp #Informix TCP/IP Socket
Step 4: Restart the Informix database service.

Get an ODBC Driver

Step 5:
Download the IBM Informix Client SDK 3.50 from IBM's download page and install.

Step 6: Set up the Informix connectivity parameters using the "Setnet32". You can launch this utility either via the shortcut in the "IBM Informix Client-SDK 3.50" folder in All Programs, or by launching it directly from C:\Program Files\IBM\Informix\Client-SDK\bin\setnet32.exe (if you didn't change the default install path).

On the "Environment" tab, click the line that reads "INFORMIXSERVER=", enter the value "tcpipserver" (without quotes) in the box that appears in the "Edit Environment Variable" section, then click the "Set" button.

On the "Server Information" tab, enter the following info:
IBM Informix Server: tcpipserver
HostName: ip address of server
Protocolname: onsoctcp
Service Name: 1526
Click the Make Default Server" button.


On the "Host Information" tab, enter the following info:
Current Host: ip address of server
User Name: enter a valid AIX username with access to the Informix database
Select "Password" in the "Password Option" dropdown list.
Password: enter the password associated with "User Name" above
Click the "OK" button.

Connect to your Informix database server

You can now either set up an ODBC connection (using the "Data Sources (ODBC)" applet in Administrative Tools - use IBM INFORMIX ODBC DRIVER as the driver for the data source), or you can set up the Informix database server as a linked server in Microsoft SQL Server. In 2005, you can use the following script to set up a linked server named "RS6000" (change the values of
[DatabaseName], [AIXUser], [AIXUserPassword], and [LocalSQLServerLogin] to appropriate values):
EXEC master.dbo.sp_addlinkedserver
@server = N'RS6000'
, @srvproduct=N'Ifxoledbc'
, @provider=N'Ifxoledbc'
, @datasrc=N'[DatabaseName]@tcpipserver'
, @provstr=N'Provider=Ifxoledbc;Data Source=
[DatabaseName]@tcpipserver;User ID=[AIXUser];Password=[AIXUserPassword];'
GO

EXEC master.dbo.sp_addlinkedsrvlogin @rmtsrvname=N'RS6000'
,@useself=N'False'
,@locallogin=NULL
,@rmtuser=NULL
,@rmtpassword=NULL
GO

EXEC master.dbo.sp_addlinkedsrvlogin
@rmtsrvname=N'RS6000'
,@useself=N'False'
,@locallogin=N'[LocalSQLServerLogin]'
,@rmtuser=N'
[AIXUser]'
,@rmtpassword='
[AIXUserPassword]'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'collation compatible'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'data access', @optvalue=N'true'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'dist'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'pub'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'rpc'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'rpc out'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'sub'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'connect timeout'
, @optvalue=N'0'
GO
EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'collation name'
, @optvalue=null
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'lazy schema validation'
, @optvalue=N'false'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'query timeout'
, @optvalue=N'0'
GO

EXEC master.dbo.sp_serveroption
@server=N'RS6000'
, @optname=N'use remote collation'
, @optvalue=N'true'
GO
You can now access this linked server from a query window with a statement like:
SELECT * FROM OPENQUERY(RS6000, 'SELECT * FROM SomeInformixTable')
Happy Hunting!