Nicolas Hanna
Nicolas Hanna

Reputation: 127

Can't use data from JSON files for datetime

So I have been trying to make a program that can display a countdown clock to a GUI. It requests a JSON file from a website and then uses that data- getting the JSON file and it's data is working for other parts of my program except using the data inside datetime.

import time
import requests
import json
import datetime as dt

response = requests.get("https://website.website/mission.json")
data = json.loads(response.text)

a = dt.datetime(data['launch'])
b = dt.datetime.now()

print("T- " + time.strftime("%H:%M:%S", time.gmtime(round((a-b).total_seconds()))))

JSON file:

{
  "mission": "GlobeSat2",
  "launch": "2020,9,13,19,00,00",
  "status": "Go"
}

When I use a = dt.datetime(data['launch']) it gives an error of TypeError: an integer is required (got type str) but when I use a = dt.datetime(2020,9,13,19,00,00) there is no error.

The value is the same as if I put it in myself

>print(data['launch'])
>2020,9,13,19,00,00

What I've tried:

I changed the value of the JSON file to "launch": "20200913120000" and gave an error of OverflowError: Python int too large to convert to C long.

I tried to do int(data['launch']) which obviously didn't work.

Upvotes: 0

Views: 242

Answers (2)

Grismar
Grismar

Reputation: 31329

Beginning programmers often make similar mistakes to yours here, confusing print statements with return values and confusing string representations of values with the actual value.

Remember that standard in and out, or the console are just a text-based user interface. They feel technical and close to the language, but they are still just a user interface.

If you run this script:

x = 123
print(123)

Or you do the same thing on the Python CLI:

>>> x = 123
>>> x
123

You might thing Python showed you the value of the x variable of type int, 123. But 123 is just the text representation of that value. There's many ways you could represent 123, for example 0b1111011 or 0x7B - all valid string representations of the exact same integer number.

Your problem is similar, in that you expect these two things to be the same:

a = dt.datetime(2020,9,13,19,00,00)

parameter = '2020,9,13,19,00,00'
b = dt.datetime(parameters)

But in the case of assigning to a, you call .datetime() with 6 integer values, while in the case of assigning to b, you call .datetime() with a single string value. The fact that the string looks very similar when printed to how you would normally write those 6 integer values in code really means nothing to Python. Note the 'when printed' vs. 'in code'.

You can have Python interpret a string to obtain the values you know it represents, but you'll have to tell it how (there's many approaches).

For example:

a = dt.datetime(*[int(part) for part in data['launch'].split(',')])

This takes the string value of data['launch'], splits it over the ',' into 6 strings in a list (['2020','9','13','19','00','00']) and then turns each part of that list into an integer with the int() function, which can turn a string that represents a single integer into its int value. The resulting list is then spread over the parameters using the * operator on the list.

There's many different approaches, but of course you could also consider fixing the JSON if you wrote the server that returned the value:

{
  "mission": "GlobeSat2",
  "launch": [2020,9,13,19,0,0],
  "status": "Go"
}

By replacing the "" with [], JSON now represents the value of "launch" as a list and when read by Python, it will be read as a list of integers.

If that was your JSON, this would be your code:

a = dt.datetime(*data['launch'])

Still using the * to spread it over the parameters of the function, but everything else would be done automatically when interpreting the JSON.

Upvotes: 0

Manish Kumar Singh
Manish Kumar Singh

Reputation: 411

If your problem is to change that date to datetime format you can easily use this one line of code to do that

a=dt.datetime(*([int(i) for i in data['launch'].split(",")]))

then a will get converted into datetime.

Upvotes: 1

Related Questions