Rustの勉強
初めてのRust
Rustのドキュメントはとてもわかり易く、言語についての理解が深まる。
さて、まずは勉強1日目、今日はチュートリアルの88ページまで読んで、言語処理100本ノックの一問目をやってみた。
文字を逆順にして返す。
fn main() { let text = String::from("hello"); //Stringで変数を定義 println!("{}", reverse(&text)); //メソッドの呼び出しと戻り値の出力(入力はString型が固定長ではないため参照で渡す。) } fn reverse(text: &str) -> String { text.chars().rev().collect() // 固定長のchar型に変換し、逆順にして、またString型に戻す。 }
Pythonがいかに何も考えずにできたかがわかる、、、Rust難しい
Gold Experience
第玖章
nvidia diriverとcudaのバージョンの相性は機械学習を行う上で一番厄介かつ、重要なポイントである。 しかし、UNIX系ではパッケージ管理システムが存在する都合上、ふとした時に全体をアップグレードしてしまうこともしばしば存在する。
sudo pacman -Syu sudo yay -Syu
この2つは全体をアップグレードするコマンドであるが、これによってnvidia driver及びcudaのバージョンが代わり相性が合わなくなるケースが存在する。 その際、どうやって再び合わせるのか、また、この2つパッケージのバージョンはどうやって固定するのか、ここでは記録として残したい。
まず、お互いの相性が悪くなった際に別々に再インストールすることで解決したが、どこまでのパッケージを再インストールすればいいか、正直よくわかっていない。
と、言うことは全体を再インストールしてやればいい。
sudo pacman -Qnq | sudo pacman -S - yay -Qnq | yay -S -
これによってpacman及びyayに管理されるパッケージはすべて再インストールされる。 環境のクリーニングという面でも都合がいいかもしれない。
これによって再インストールされた後は再起動することでパッケージ同士のバージョンが安定する。
では、次にバージョンが安定すれば、このような悲劇がもう起きないように、パージョンを固定してやればいい。 固定するパッケージは/etc/pacman.confのIgnorePkg に記述する必要がある。
私は以下の様に記述している。
IgnorePkg = cuda cudnn lib32-nvidia-utils linux510-nvidia nvidia-utils
これによって"おそらく"パッケージのバージョンが固定されるはずである。
さぁ、やっとBERTをGPUを用いて扱うことができる。
Gold Experience
第肆章
cudaのバージョンの最新が11.0から11.1に上がっていた。おかげでDockerのcudaイメージを叩いても、cudaとのネットワークがつながっていない。 なので、cudaのバージョンを上げようとしたが、nvidia-driverのバージョンから上がっていたようだ。 なので、nvidia系のパッケージをすべて削除、最新で入れ直した。 そしたらどっこい、nvidia-smiすら認識しなくなった。driverが死んだ。
悩んだ挙げ句、一つの必殺技を見つけた。
sudo pacman-mirrirs --fasttrack && sudo pacman -Syyu
おそらくpacmanの中で溜まったゴミを一層し、すべてのパッケージを入れ直してくれる、、、ようなイメージ(詳細は調べてない、すみません)。 これで、最新のnvidia系パッケージが正常にインストールできそう。 ただし、nvidia-455とカーネルlinux58及びlinux59は相性が悪いそう。 なので、、やっぱりPython同様7系のバージョンが安定しているようだ。
第伍章
逝った。なにがって?GPUが逝った。 モニターに描画されない。 状況をわかりやすく説明すると、GPUにhdmiとディスプレイポートの端子をつないでモニターに接続している。 PCの電源を起動してすぐ、GRUB2によるカーネルの選択画面になり、その後真っ暗になるのだ。 どのカーネルを選択してもダメ、仕方なく "Alt + F2" でCUIモードを起動する。 なんでこういう描画はされるのに、他はダメなんだ、、、
ふと気づくとカーネルlinux56が消えている。俺の安定版だったのに。。。 記憶をたどると "sudo pacman -Syu" をした際カーネルがインストールされていた。 たしか、linux59だったか、、、しまった、最新のデフォルトカーネルが更新されて、同時にlinux56が削除されてしまったのか。。。
消えてしまったものに、思いを馳せても仕方ないので、最新のカーネル(linux59)で再度環境構築を行う。
ちなみにマザボにディスプレイを設定してみた結果、"Could not start simple desplay"などと記述されていたので結局大本のディスプレイドライバが死んでいる気がする。 というわけで、もう仕方ないので、nvidia系のすべてのパッケージを殺すことにした。
sudo pacman -Qs nvidia # インストールされているnvidiaパッケージをすべて出力する。 sudo pacman -Rs ???? # パッケージを依存関係ごと消去していく。 sudo pacman -S nvidia sudo pacman -S cuda sudo pacman -S cudnn
これでrebootすると、、、行けた。 今回の原因はカーネルのバージョンが変わったことで各パッケージも変わっていたのにパッケージを増やすばかりで取捨選択をしなかったことだった。 ちゃんと定期的にパッケージの取捨選択を行わないといけなかったわけだ。
いずれにせよ、OSを飛ばさなくて済み良かった。 デフォルトのカーネルの更新が早いので、これはいい教訓になったと思う。
第陸章
また逝ったよ。もちろんGPUです。 モニターが真っ暗ですわ。 原因は簡単。linux59のカーネルで今まで動かしてきたのに、興味本位でlinux510のカーネルを立ち上げたのが原因だった。 次にlinux59で起動したとき、HDDが読み込めなくなっていたほか、様々なトラブルが起きて立ち上がることさえなかった。 こうなってはもうやることは一つ、linux510で再構築するしかない。
再構築の手順は第伍章のとおりである。 そして文字コードがGUIとは管轄が違うようなので、合わせることが必要になる。 コマンドは以下
LANG=C
また、"sudo pacman -Rsで消えないパッケージも存在した。
- local/mhwd-nvidia-390xx 390.143-1 MHWD module-ids for nvidia 390.143
- local/libvdpau 1.4-1 Nvidia VDPAU library
この2つは依存関係からどうも消去できない。(依存先を消していいものかわからない) まぁ、干渉してこないようなので、放置だ。
nvidiaには何度も悩まされるが、この情報があればなんとかなるだろう。
第漆章
今度はパッケージ更新した際に、HDMIから音声がでなくなった。 フォーラムでこの課題について確認すると同じ症状の人がいた。(https://forum.manjaro.org/t/hdmi-audio-isnt-working-on-an-asus-laptop/63320/50)
結果的に解決策としては、以下の2コードを打ち込むだけだった。
amixer -c0 sset 'Auto-Mute Mode' Disabled rm ~/.config/pulse/cookie ~/.config/pulse/*.tdb
ただ、このコマンドは該当パッケージが更新されるたびに打ち込む必要があるので注意。
第捌章
???「我々はひとつのOSを失った。しかし、これは廃棄を意味するのか?否!始まりなのだ! windowsユーザに比べ、我がmanjaroのユーザは30分の1以下である。 にもかかわらず今日まで使いこなしてこられたのは何故か? 諸君!我がmanjaroの使用目的が正義だからだ。これは諸君らが一番知っている。 我々は世界的シェアを追われ、ニッチなOS扱いにさせられた。 そして、一握りの企業らが世界的シェアにまで膨れ上がったwindowsを支配して50余年、 OS界の辺境に住む我々が自由を要求して何度踏みにじられたか。 manjaroの掲げるOS一つ一つの自由のための戦いを神が見捨てるはずはない。 私のOS!諸君らが愛してくれたmanjaroは飛んだ。 何故だ!?」
???「BIOSをアップデートしたからさ」 ※ 機動戦士ガンダム作中 manjaro追悼式典より
というわけで、manjaroが飛んだ 理由は前述の通りBIOSをアップデートしたからだ。
BIOSをアップデートする経験は初めてで、なんとなくアップデートしたのは間違いだった。 原因はアップデートした際、BIOSの設定が初期化されmanjaroが入ったSSDが読み込めなくなる。 ただ、それだけだったのだが、、、
原因を突き止められなかった私は、manjaroを起動できず、データすら取り出すことができなかった。 その結果、OSの再インストールを決めた(なので、飛んだ原因は私)。
だが悲劇はまだ続く manjaroがSSDをロックしており、外部から削除することができなかった。 また、削除する過程で、SSDに上書きを行った結果、実は上書きしたSSDがmanjaroではなく、操作中のwindowsだった。
そう、そもそも同じ型番のSSD、まさかwindows SSDが表示されており、それを操作しているとは微塵にも思っていなかった(マシンの理解不足)。 かくして、私は2つのOSを失った。
そして、更にその2つのSSDがBIOSから姿を消した。 認識しなくなったのである。
流石にお手上げと思い、父に相談するが、SSDを物理的に壊したのではないかとの回答 そんなことがあるのか?たった数行のコマンドでSSDが物理的に、、、?
まさか、ありえない、そう思い探しまくり2日 見つけた。 これだ。
結果的には、以下の3つの設定を変更することで解決した。
もう二度とこんなことごめんだ。 バックアップは適宜取るように心がけたい。
Gold Experience
これはubuntuしか触ったことのない少年がmanjaroと出会い、成長していくストーリーである。
第零章 : PUROROGE
まず私は、自分がintel core-i9 10850Kを購入したことに感謝したい。 manjaroは、インストール直後nvidia driverは入っていないため、GPUに接続されたモニタは機能しないのだ。 そこで、core-i9の "K" の出番である。"K" には、CPUに最低限のGPUが内蔵されている。 私はそのおかげで、マザーボードに接続されたモニタでmanjaroの設定を行うことができた。
第壱章 : INSTALLER
ubuntuは、いい。わからないときには、調べれば初心者用の記事が数多く出てくる。 しかし、デザインが好きではなかった。私はubuntuに飽きてしまったのだ。 その日私は、ubuntuの環境構築を行っていた。もうやりなれた作業で、淡々とこなしていたが、GPUの環境構築でしくじった。 最近よく見るubuntuの環境構築記事はAWSを対象に書いている記事も多い。 私は、誤ってそちらの記事を参考にnvidiaのドライバをいれてしまった。 結果、GPUは正常に作動していたが、描画用に機能する設定はできていなかったのである。
そこで、ラボのシス管はこういった。 「manjaroにしましょう。」と。 manjaroとは、そもそもArch-linux系のカーネルで、ubuntuはdebian系のカーネルである。 同じlinuxでも、どの程度ubuntuの経験が通用するか不安で、はじめは渋った。 しかし、彼のmanjaroに対する熱い想いに押され、私はついにmanjaroに手を出したのだった。
manjaroのインストーラには4つのタイプがある。
これはX-windowのデザインを選択させている。また、CUIアーキテクチャだけを最初にインストールし、自分で詳細を細かく設定することもできる。 私は、この中でシス管の彼が使用していたplasmaを入れることにした。
第弐章 : INSTALL
パッケージを入れたUSBから、インストーラを起動した。 GRUB2のブートローダからmanjaroを選択し、OSを起動させた。 しかし、真っ黒な背景にBIOSのアイコンが画面中央に表示されたまま止まった。 しばらくして、紫色のノイズが画面上に走り、真っ黒な背景を半分に割ったのだった。 モニタから出たHDMIケーブルはGPUに接続されていた。
何度再起動しても、画面にはノイズが走る。原因がわからない。 そこで、CUIのインストーラをUSBに入れ、再度試した。 しかし、GRUB2のブートローダが起動するのは、CUIアーキテクチャとて変わらない。 結果は、失敗だった。
時刻はその時26時を回っていた。 眠気がじわじわと押し寄せる中、ふとマザーボードのHBMIポートにケーブルを挿し直した。 すると、きれいな細かい文字が下から上へサーっと流れ、manjaroのインストーラが起動したのだった。
起動した感動で眠気が飛び、manjaroのM.2 SSDへのインストールを淡々とボタンをポチポチと押し、実行した。 ここで、問題が出た。 インストーラが95%で止まったのだ。 ちょうどその時シス管の彼が3時間前に投稿されたmanjaroのバグについて読んでいた。 同じ症状だった。解決策はまだ立っていなかったので、強制シャットダウンし、インストールされたmanjaroを起動してみた。
更新されていないパッケージが500件ほどあったが、問題なく動作している。 もしやイけるのでは...?
第参章 : PACKAGE
ここでubuntuとの違いだが、ubuntuのパッケージ管理システムはaptだが、manjaroはpacmanである。 これがうまく動作すれば、おそらく大丈夫だろうと考え、まずはパッケージの更新を行った。
sudo pacman -Syu #全パッケージのアップグレードとリフレッシュ
これを行うことで、95%で固まったインストーラの残りのタスクを保管できていると思っている。(実際更新されたパッケージは500個ほどあり、インストール直後にあった未更新のパッケージ数とほぼ一致した。)
さぁ、ここからは自分の欲しいパッケージのインストール作業である。 私のPCには、RTX2070SUPERが入っているのですが、現状モニタに接続されているのは、マザボであるためGPUからモニタ接続したい。 欲しいパッケージは - nvidia-driver-450.66 - cuda11 - cuDnn8 の3つである。 ubuntuであれば、CUDAのインストールまでがOSのインストールだと思っている。 というのは、慣れるまではCUDAのインストールがとても骨が折れる作業なのである。 しかし、manjaroはその限りではない。なぜなら "pacman"がいるからである。 上記3つのインストールは
sudo mhwd -i pci video-nvidia-450xx sudo pacman -Syu cuda sudo pacman -Syu cudnn
以上である。 素晴らしい。ubuntuのあの努力は何だったのか。 あぁ、、、もっと早くmanjaroを知りたかった。 他にもメジャーなパッケージはpacmanを用いれば簡単にダウンロードできるそうだ。 あぁ、感動だ。 今回はこれで以上にしたい。 manjaroを紹介してくれたシス管の彼には本当に感謝したい。ありがとう。
就活サイトからESをかっさらってくる。
最近、機械学習用の言語データがないかなーって探していたんですけど、いい情報がなくて諦めていました。 そしたらたまたま、いい記事を見つけたので真似をしてみることに。
それがこちらの記事 この記事はunistyleに公開されているESをスクレイピングによって取得するというものでした。
しかし、この記事は2年前に執筆されており、実行すると不具合が出ました。 そこで、コードを修正(コードの可読性、効率は悪くなった、、、)し、ここに記録として載せました。
それが以下のコード
#coding:utf-8 PURPLE = '\033[35m' RED = '\033[31m' CYAN = '\033[36m' OKBLUE = '\033[94m' OKGREEN = '\033[92m' WARNING = '\033[93m' FAIL = '\033[91m' ENDC = '\033[0m' from selenium import webdriver from selenium.webdriver.chrome.options import Options import time from bs4 import BeautifulSoup from extractcontent3 import ExtractContent import pickle import sys ##### ExtractContent(only fetch contents)######## def extractor(html): extractor = ExtractContent() opt = {"threshold":50} extractor.analyse(html) text, title = extractor.as_text() return text email = 'USER_ID' password = 'USER_PASSWORD' LOGIN_URL= 'https://unistyleinc.com/' # Log in options = Options() options.binary_location = "/usr/bin/google-chrome" b = webdriver.Chrome(chrome_options = options, executable_path='./chromedriver') b.get(LOGIN_URL) b.find_element_by_id('LoginLink').click() b.find_element_by_name('user[email]').send_keys(email) b.find_element_by_name('user[password]').send_keys(password) b.find_element_by_class_name('login_submit').click() def first(): # Move to categories time.sleep(0.1) b.get('https://unistyleinc.com/categories') category = b.find_element_by_class_name('es_category_list') a = category.find_elements_by_css_selector("a") dict_category = {} for total,i in enumerate(a): if not total == int(category_num): continue name = str(i.text.replace('>','')) URL = str(i.get_attribute("href")) print ('STEP1 : '+str(total+1)+'/'+str(len(a))+' '+name+'--->'+OKBLUE+URL+ENDC) dict_category[name]=URL # Move to company from the category dict_company = {} for name in dict_category: URL = dict_category[name] b.get(URL) time.sleep(0.1) companies = b.find_element_by_class_name('essearch_common_wrap') a = companies.find_elements_by_css_selector("a") for i in a: company = str(i.text.split(' ')[0]) URL = str(i.get_attribute("href")) if URL != 'https://unistyleinc.com/categories': dict_company[company] = URL print ('STEP2 : '+company+'--->'+OKGREEN+URL+ENDC) # 本選考などESpageを取得 dict_kindofES = {} for company in dict_company: URL = dict_company[company] b.get(URL) time.sleep(0.1) ESs = b.find_element_by_class_name('essearch_common_wrap') a = ESs.find_elements_by_css_selector("a") count = 0 for i in a: cmp = str(i.text.split(' ')[0]) URL = str(i.get_attribute("href")) if count != 0 and URL != 'https://unistyleinc.com/categories': dict_kindofES[company+cmp] = URL print ('STEP3 : '+company+cmp+'--->'+OKGREEN+URL+ENDC) count = count + 1 # Move to (ES/interview/OB visit etc...)page from company URL dict_com_url = {} for company in dict_kindofES: URL = dict_kindofES[company] b.get(URL) def get_ES_URL(b,dict_com_url): time.sleep(0.1) list_ES = b.find_elements_by_class_name('es_container') for i in list_ES: a = i.find_element_by_css_selector("a") url = str(a.get_attribute("href")) print ('STEP4 : '+company+'--->'+PURPLE+url+ENDC) dict_com_url.setdefault(company, []).append(url) ES_page_number = b.find_elements_by_class_name('fg essearch_page_btn') if not len(ES_page_number) == 0: for epn in ES_page_number: a = epn.find_element_by_css_selector("a") EsPageUrl = str(a.get_attribute("href")) b.get(EsPageUrl) get_ES_URL(b,dict_com_url) else: get_ES_URL(b,dict_com_url) with open('./dict_com_url.pickle', mode='wb') as f: pickle.dump(dict_com_url,f) def second(): with open('./dict_com_url.pickle', mode='rb') as f: dict_com_url = pickle.load(f) #Save contents W = open('result'+args[2]+'.csv','w') W.write('ID,Company,URL,Contents\n') num = 0 code = 0 dict_com_url_count = 0 for key in dict_com_url: list_URL = dict_com_url[key] for j,URL in enumerate(list_URL): try: b.get(URL) time.sleep(0.1) html = b.page_source text = extractor(html) # text = text.replace(',','').replace('\n',' ').replace('\t','').replace('\r','') text = text.replace(',',',') print ('STEP5 : '+key+'--->'+PURPLE+URL+ENDC) print (text[:100]+'...') W.write(str(num)+','+key+','+URL+','+text+'\n') except: # print ('request error') code = 1 break num+=1 if code == 1: print("システムが終了しました。\n最終実行はdic_com_url:"+str(dict_com_url_count)+"番のlist_URL:"+str(j)+"番です。") break dict_com_url_count += 1 W.close() def therd(): with open('./dict_com_url.pickle', mode='rb') as f: dict_com_url = pickle.load(f) #Save contents W = open('result'+args[2]+'.csv','a') num = int(args[3]) code = 0 dict_com_url_count = 0 for i,key in enumerate(dict_com_url): if i >= int(args[3]): list_URL = dict_com_url[key] for j,URL in enumerate(list_URL): if i == int(args[3]) and j < int(args[4]): continue try: b.get(URL) time.sleep(0.1) html = b.page_source text = extractor(html) text = text.replace(',',',') print ('STEP5 : '+key+'--->'+PURPLE+URL+ENDC) print (text[:100]+'...') W.write(str(num)+','+key+','+URL+','+text+'\n') except: code = 1 break num+=1 if code == 1: print("システムが終了しました。\n最終実行はdic_com_url:"+str(dict_com_url_count)+"番のlist_URL:"+str(j)+"番です。") break dict_com_url_count += 1 W.close() args = sys.argv category_num = args[2] if args[1] == "1": first() elif args[1] == "2": second() elif args[1] == "3": therd() else: print(args+"が入力されました\n第一引数:シーケンス番号,第二引数:カテゴリ番号,第三引数:中途開始番号1,第四引数:中途開始番号2")
このコードは2回、ないし3回実行することが必要です。
実行は
python3 Scraping.py 1 [企業カテゴリ番号(0-35)] python3 Scraping.py 2 [企業カテゴリ番号(0-35)]
しかし、seleniumの影響でスクレイピング数が変化します。 なので、もし途中で止まった場合、どこで止まったか最後に表示するようにしているので、 その続きから実行するために
python3 Scraping.py 3 [企業カテゴリ番号(0-35)] [中途開始番号1] [中途開始番号2]
として、エラーなく最後まで実行できるようにします。 また、これでもまだ途中で止まる可能性があるので、その場合は途中開始番号1に前回の途中開始番号1を足した値を入れてあげることで またその続きから実行できます。
お粗末な改修プログラムですが、誰かのお役にたてますように
Raspberry piとBluetoothスピーカでSpotifyプレーヤーをつくってみた。
今回は家にあるRaspberry pi4の活用方法を考えていましたが、IKEAでBluetoothスピーカーを買ったことをきっかけに音楽プレーヤーを作ってみました。
その方法をここに記したいと思います。
まずは、使用したもののリスト
Raspberry pi4 OS:ubuntu Server 20.04.2 LTS IKEA Bluetoothスピーカー:ENEBY30 SONY PaSoRi RC-S380
なぜカードリーダーが使用リストに入っているのか。
それは、帰宅して玄関のリーダーにカードをかざすとSpotifyから曲が再生されるようにしたからです。(とりあえず使いたかった。)
さぁ、まずはじめにBluetoothスピーカーと接続します。(Raspberry piの基本的なセットアップはすでにできている程で進めます) 特筆して入れたのはneovim くらいですね。また、プログラムはpython3.8で組んでいます。 ここで参考にしたのはここです。 この記事はAmazon Echoでやっていますが、通常のBluetoothスピーカでも同じでした。
特筆すべき点として、この記事の"Amazon EchoとのBluetooth接続を維持する"の項で記されている以下のコードを修正します。 理由は、どうもエラーをはいてうまく動作していなかったからと、私のスピーカーが20分で電源が切れるので、15分程度でいいかなと思ったからです。
修正前
$ crontab -e ----- 追加 ----- */5 * * * * /usr/bin/aplay/aplay -q -D bluealsa /home/nosound.wav >/dev/null 2>&1
修正後
$ crontab -e ----- 追加 ----- */15 * * * * aplay -q -D bluealsa /home/nosound.wav >/dev/null 2>&1
ちなみに >/dev/null 2>&1 がどういう意味なのか興味があって調べてみると、標準出力をカットするみたいです。参考
つぎにカードリーダで学生証を読み取れるようにします。 なぜ学生証か、余ってるからです。
先に参考とした記事はこちらです。
main.py
import sys import binascii import nfc import requests import json import demo3 import time import subprocess #弊学の学生証の学籍番号が格納されているサービスコード service_code = 0x0A0B def connected(tag): if isinstance(tag, nfc.tag.tt3.Type3Tag): try: #16ビットのservice_codeからservice >> 6で上位10ビットを取り出し、service_code && 0x3fで下位6ビットを取り出す svcd = nfc.tag.tt3.ServiceCode(service_code >> 6, service_code & 0x3f) #serviceはread_without_encryptionの引数service_list内でのインデックス blcd = nfc.tag.tt3.BlockCode(0,service=0) #read_without_encryptionでタグの指定した部分の情報内のブロックデータを読み取る block_data = tag.read_without_encryption([svcd], [blcd]) #今回ではブロックデータの1文字目から8文字目に格納されている、それを文字列に変換しutf-8でデコード student_id = str(block_data[0:8].decode("utf-8")) print(student_id) except Exception as e: print("Error:%s" % e) else: print("Error:tag isn't Type3Tag") #値をTrueで返すと触れて離すまでの間、一回だけ処理を行う return True clf = nfc.ContactlessFrontend('usb') def main(): bool = False while True: #学生証を読み取るまで待機 clf.connect(rdwr={'on-connect': connected,}) send.send_message(bool) if bool == True: # Falseは出勤、Trueは帰宅 print("帰宅") demo3.play() bool = True else: print("出勤") try: demo3.pause() except: pass bool = False try: main() except KeyboardInterrupt: print("Forced termination") clf.close() sys.exit(0)
以上がmainプログラム。この中でimportされているdemo3.pyでspotifyを操作します。 参考はここ ここのプログラムはアーティスト名から勝手にプレイリストを作成してくれますが、プレイリストが多くなるので以下の様に変更しました。
demo3.py
import spotipy import spotipy.util as util import sys import random import subprocess import requests import json def play(): #再生 username = "hogehoge" scope = 'user-read-playback-state,playlist-read-private,user-modify-playback-state,playlist-modify-public' token = util.prompt_for_user_token(username, scope) header = {'Authorization': 'Bearer {}'.format(token)} res = requests.get("https://api.spotify.com/v1/me/player/devices", headers=header) devices = res.json() device_id = devices["devices"][0]['id'] playlist_id = 'HOGEHOGE' #プレイリストのURLの最後の/以下の文字列 param = {'device_id':device_id, 'context_uri':'spotify:playlist:%s' % playlist_id} res = requests.put("https://api.spotify.com/v1/me/player/play", data=json.dumps(param), headers = header) def pause(): #停止 username = "hogehoge" scope = 'user-read-playback-state,playlist-read-private,user-modify-playback-state,playlist-modify-public' token = util.prompt_for_user_token(username, scope) header = {'Authorization': 'Bearer {}'.format(token)} res = requests.get("https://api.spotify.com/v1/me/player/devices", headers=header) devices = res.json() device_id = devices["devices"][0]['id'] playlist_id = 'HOGEHOGE' #プレイリストのURLの最後の/以下の文字列 param = {'device_id':device_id, 'context_uri':'spotify:playlist:%s' % playlist_id} res = requests.put("https://api.spotify.com/v1/me/player/pause", data=json.dumps(param), headers = header)
これによって、カードをかざすたびに、再生、停止が行えます。
ただし、気をつけなければいけないことが一つ。 rebootなどを行った際は、必ずケータイかPCのspotifyからraspotiyを選択して曲を再生、停止してからプログラムを実行させてください。
これで、完成です。 とってもざっくりな解説でしたが、誰かのお役に立てれば幸いです。
以上。