Casting date in Nodejs mssql does not work - node.js

I am trying to remove timestamp from a data column. I can do that in SQL Server Management Studio doing:
select CAST(GETDATE() as date)
Now, when I try to do the same thing using Nodejs-MSSQL library I get the time stamp as well:
await pool.query(` select CAST(GETDATE() as date)`)
Can someone please explain how this is even possible?

Related

postgresql to_char(date, 'day') get different result when using nodejs

UPDATE 2
Using the suggestions from #Bergi, I added a db execution helper to set the timezone before executing the query. This allows me to control the timezone based on the logged in user's preferences.
async function execWithTZ(sql, params, timezone) {
const client = await this.pool.connect();
await client.query<any>(`SET TIMEZONE TO '${timezone}'`, []);
return client.query<any>(sql, params);
}
const result = await execWithTZ('SELECT ...', [], 'Australia/Sydney');
QUESTION
I am trying to get Postgresql to return the day of the week of a specific date in a view. I later use this to display values by day.
The data is in a table with a column named updated which is a timestamptz field.
When running the following query using DBeaver SQL client against a PostgreSQL 12 database I get the values as I expect, with records updated on Thursday local time (just after midnight) showing up as Thursday
SELECT
count(v.id) AS count,
btrim(to_char(v.updated, 'DAY'::text)) AS day,
date_trunc('DAY'::text, v.updated) AS "updatedDay"
FROM table v
GROUP BY (to_char(v.updated, 'DAY'::text)), (date_trunc('DAY'::text, v.updated))
I put this in a view and when I query this view using node-postgres the counts are for the previous day (Wednesday), which I presume is because the database thinks it should interpret the dates in the UTC timezone.
To further prove the point, when I change the above query to use DAYTZ instead of just DAY in DBeaver I get THURSDAYAEST but in nodejs as result I get WEDNESDAYUTC
Changing all my dates to be without timezone and forcing everything to UTC on the way in is not an option for me.
How can I make node-postgres tell the database what timezone I want these dates interpreted as so that I can get the correct day?
UPDATE 1
I managed to get PostgreSQL to return the correct values to postgres node by setting the database user's timezone.
ALTER ROLE visuo_ingest SET TIMEZONE TO 'Australia/Sydney';
Now the counts for things that happened on Thursday Sydney time is counted for Thursday and not Wednesday.
Still interested in a way to do this on the connection rather than the database user level.
Still interested in a way to do this on the connection rather than the database user level.
You already found the right setting, there's no reason to alter it on a role only. You can also change the setting in a client session by running the SET command
SET TIMEZONE TO 'Australia/Sydney';
Just put that in a pgClient.query("…"); right after connecting the client.

How to set Knex date to 30 days in the future

I think this question is simple really but I wasn't able to find an answer for it.
In Knex i could set a timestamp in my database with knex.fn.now()
However now I have a need to set a date 30 days after now is this as simple as knex.fn.now() + 30 work or is there another trick?
Any help is appreciated even a link to a different source.
Thank you in advance
knex.fn.now() will execute CURRENT_TIMESTAMP function on the db, which returns timestamp in ms from 1/1/1970.
You can use a db built in method for calculating future dates.
In MySQL this method calls date_add.
SELECT date_add(now(), INTERVAL 30 day);
With Knex you will need to use the raw method.
knex.select(knex.raw('date_add(?, INTERVAL ? day)', [knex.fn.now(), 30]));
Edit:
In postgress, this query will look like:
SELECT CURRENT_DATE + INTERVAL '1 day';
so, in Knex it will be:
knex.select(knex.raw(`? + INTERVAL '? day'`, [knex.fn.now(), 30]));
Thank you for the previous answer, but that Postgresql example didn't work for me.
When I tried knex.raw(`? + INTERVAL '? day'`, [knex.fn.now(), 30]), I got an error "could not determine data type of parameter"
This worked:
knex.raw(`? + ?::INTERVAL`, [knex.fn.now(), '30 day'])

Return the item number X in DynamoDB

I would like to provide one piece of content per day storing all items in dynamoDB. I will add new content from time to time but only one piece of content needs to be read per day.
It seems it's not recommended to have incremental Id as primary key on dynamoDB.
Here is what I have at the moment:
content_table
id, content_title, content_body, content_author, view_count
1b657df9-8582-4990-8250-f00f2194abe9, title_1, body_1, author_1, view_count_1
810162c7-d954-43ff-84bf-c86741d594ee, title_2, body_2, author_2, view_count_2
4fdac916-0644-4237-8124-e3c5fb97b142, title_3, body_3, author_3, view_count_3
The database will have a low rate of adding new item has I will add new content myself manually.
How can I get the item number XX without querying all the database in nodeJS ?
Should I switch back to a MySQL database ?
Should I use a homemade auto increment even if it's an anti pattern ?
Should I used a time-based uuid, and do a query like, get all ids, sort them, and get the number X in the array ?
Should I use a tool like http://www.stateful.co/ ?
Thanks for your help
I would make the date your hash key, you can then simply get the content from any particular day using GetItem.
date, content_title, content_body, content_author, view_count
20180208, title_1, body_1, author_1, view_count_1
20180207, title_2, body_2, author_2, view_count_2
20180206, title_3, body_3, author_3, view_count_3
If you think you might have more than one piece of content for any one day in future, you could add a datetime attribute and make this the range key
date, datetime, content_title, content_body, content_author, view_count
20180208, 20180208101010, title_1, body_1, author_1, view_count_1
20180208, 20180208111111, title_2, body_2, author_2, view_count_2
20180206, 20180208101010, title_3, body_3, author_3, view_count_3
Its then still very fast and simple to execute a Query to get the content for a particular day.
Note that due to the way DynamoDB distributes throughput, if you choose the second option, you might want to archive old content into another table.

Forcing a string field to DateTime in WCF query with Azure Table Storage

So, a quick overview of what I'm doing:
We're currently storing events to Azure Table storage from a Node.js cloud service using the "azure-storage" npm module. We're storing our own timestamps for these events in storage (as opposed to using the Azure defined one).
Now, we have coded a generic storage handler script that for the moment just stores all values as strings. To save refactoring this script, I was hoping there would be a way to tweak the query instead.
So, my question is, is it possible to query by datetime where the stored value is not actually a datetime field and instead a string?
My original query included the following:
.where( "_timestamp ge datetime'?'", timestamp );
In the above code I need to somehow have the query treat _timestamp as a datetime instead of a string...
Would something like the following work, or what's the best way to do it?
.where( "datetime _timestamp ge datetime'?'", timestamp );
AFAIK, if the attribute type is String in an Azure Table, you can't convert that to DateTime. Thus you won't be able to use .where( "_timestamp ge datetime'?'", timestamp );
If you're storing your _timestamp in yyyy-MM-ddTHH:mm:ssZ format, then you could simply do a string based query like
.where( "_timestamp ge '?'", timestamp );
and that should work just fine other than the fact that this query is going to do a full table scan and will not be an optimized query. However if you're storing in some other format, you may get different results.

Subsonic 3.0 SQLite FormatException parsing DateTime?

I have an MS Access database, which I have converted to an SQLite database. I have SubSonic setup and working, and I can pull data out of the database successfully into a WinForms app using ActiveRecord. All except for one table.
I get a FormatException, "String was not recognized as a valid DateTime". The format of the date column in the database is DD/MM/YYYY.
I'm not even trying to do anything too complicated:
var allOrders = order.All();
foreach (order o in allOrders)
{
listBox1.Items.Add(string.Format("{0} - {1}", o.OrderDate.HasValue ? o.OrderDate.Value.ToShortDateString() : string.Empty, o.Product));
}
I'm not exactly sure why the problem is manifesting in the first place :(
SQLite has "interesting" ways of formatting dates - you have to be very, very sure that you're getting back what you think you are because normally it's not DD/MM/YYYY - it's the opposite if I recall.

Resources