質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
Discord

Discordは、ゲーマー向けのボイスチャットアプリです。チャット・通話がブラウザ上で利用可能で、個人専用サーバーも開設できます。通話中でも音楽を流したり、PC画面を共有できるなど多機能な点が特徴です。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

1回答

5012閲覧

Discord.pyでjson.decoder.JSONDecodeError: Expecting value: line 2 column 1 (char 4)が発生する

Unknown_P

総合スコア1

Discord

Discordは、ゲーマー向けのボイスチャットアプリです。チャット・通話がブラウザ上で利用可能で、個人専用サーバーも開設できます。通話中でも音楽を流したり、PC画面を共有できるなど多機能な点が特徴です。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2020/10/21 17:36

Discord.pyで天気を表示するBOTを作成しているのですが、
実行するとタイトルのエラーコードが表示され実行できません。
どうすればよいでしょうか。

発生している問題・エラーメッセージ

Ignoring exception in on_message Traceback (most recent call last): File "C:\Users*\AppData\Local\Programs\Python\Python38\lib\site-packages\discord\client.py", line 312, in _run_event await coro(*args, **kwargs) File "C:\Users*\Downloads\天気.py", line 40, in on_message resp = json.loads(resp.decode('utf-8')) File "C:\Users*\AppData\Local\Programs\Python\Python38\lib\json\__init__.py", line 357, in loads return _default_decoder.decode(s) File "C:\Users*\AppData\Local\Programs\Python\Python38\lib\json\decoder.py", line 337, in decode obj, end = self.raw_decode(s, idx=_w(s, 0).end()) File "C:\Users*\AppData\Local\Programs\Python\Python38\lib\json\decoder.py", line 355, in raw_decode raise JSONDecodeError("Expecting value", s, err.value) from None json.decoder.JSONDecodeError: Expecting value: line 2 column 1 (char 4)

該当のソースコード

python

1#coding=SHIFT-JIS 2import discord 3import urllib.request 4import json 5import re 6 7client = discord.Client() 8 9citycodes = { 10 "土浦": '080020', 11 "水戸": '080010', 12 "札幌": '016010', 13 "仙台": '040010', 14 "東京": '130010', 15 "横浜": '140010', 16 "名古屋": '230010', 17 "大阪": '270000', 18 "広島": '340010', 19 "福岡": '400010', 20 "鹿児島": '460010', 21 "那覇": '471010' 22} 23 24@client.event 25async def on_ready(): 26 print("天気") 27 print(discord.__version__) 28 29@client.event 30async def on_message(message): 31 if message.author != client.user: 32 33 reg_res = re.compile(u".w (.+)").search(message.content) 34 if reg_res: 35 36 if reg_res.group(1) in citycodes.keys(): 37 38 citycode = citycodes[reg_res.group(1)] 39 resp = urllib.request.urlopen('http://weather.livedoor.com/forecast/webservice/json/v1?city=%s'%citycode).read() 40 resp = json.loads(resp.decode('utf-8')) 41 42 msg = resp['location']['city'] 43 msg += "の天気は、\n" 44 for f in resp['forecasts']: 45 msg += f['dateLabel'] + "が" + f['telop'] + "\n" 46 msg += "です。" 47 48 await client.send_message(message.channel, message.author.mention + msg) 49 50 else: 51 await client.send_message(message.channel, "対応地域ではありませんでした。\n下記リストから再度検索を行ってください。\n```土浦/水戸/札幌/仙台/東京/横浜/名古屋/大阪/広島/福岡/鹿児島/那覇```")

試したこと

respに代入しているリンクが存在していなかったため、別のリンクなどを使用しましたが対応できませんでした。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

短い回答(tl;dr)

livedoor 天気はサービスを終了しました。代わりにYahoo! JAPANが提供する気象情報APIなどをご利用ください。

長い回答

調査

シェルでcurl -Iというコマンドを使用し、レスポンスを確認すると302 Foundと表示されます。これはHTTPレスポンスステータスコードと呼ばれるもので、数字が3xx(300〜399の間)のものはリダイレクト(転送)を意味します。

sh

1$ curl -I 'http://weather.livedoor.com/forecast/webservice/json/v1?city=130010' 2HTTP/1.1 302 Found 3Date: Wed, 21 Oct 2020 23:57:18 GMT 4Server: Apache 5Location: http://www.livedoor.com/?city=130010 6Connection: close 7Content-Type: text/html; charset=iso-8859-1`

転送先であるhttp://www.livedoor.com/?city=130010をcurlで取得して、頭の2行を読んでみましょう。

sh

1$ curl -s 'http://www.livedoor.com/?city=130010' | head -n 2 | bat -An 2 1 ␍␍␍␊ 3 2 <!DOCTYPE·html>␍␊

1行目の内容はの4文字、そして2行目からはHTMLのタグが開始しています。これはJSONではありませんね。

解説

ここでタイトルにも載っているエラーメッセージを確認しましょう。

plain

1json.decoder.JSONDecodeError: Expecting value: line 2 column 1 (char 4)

パーツごとに分けて説明します。

json.decoder.JSONDecodeError:

JSONDecoderがJSONDecodeErrorを出しています。これはJSONのデコード中にエラーが発生したことを意味します。

Expecting value:

エラーの実メッセージ部です。値を期待したが、それが得られなかったことを意味します。

line 2 column 1 (char 4)

エラーの発生箇所です。Pythonにとっての4番目の文字、人間にとっての2行目1列目を読もうとしたところでエラーが発生したことを意味します。

これに該当する文字は<です:

plain

1 1 2 ␍␍␍␊ 32 <!DOCTYPE·html>␍␊

まとめ

JSONDecoderはプログラムがlivedoor 天気のAPIから受け取ったレスポンスをJSONとして読もうとしました。しかし、最初に発見した意味のある文字は<で、これはJSONの構文としてありえないものでした。結果として、「JSONの値を期待したけど、受け取れなかった」と言う内容のエラーを発生させました。この問題を修正するためには、短い回答にも書いてあるように問い合わせ先のAPIを正しくJSONを返答してくれるものに変更する必要があります。

投稿2020/10/22 01:24

itepechi

総合スコア248

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問