LoginSignup
2
3

More than 5 years have passed since last update.

自分のツイートだけを保存していく不毛なTwitter投稿クライアント

Last updated at Posted at 2017-05-16

自分のツイートだけを保存する

結局のところ何のために利用するかはわからないですが、Djangoのフォーム・テンプレートなどの理解を進めるにはやっぱりTwitterAPIで遊ぶのが最適解なのではないかなと思っています。というか何回Twitter APIで遊ぶんだよ、っていうのはやめてください。自覚症状はあります。

Djangoプロジェクトを作成する

Python3.6を想定しているので仮想環境構築は楽するやつ。

$ python3 -m venv pyworks
$ ls pyworks/
$ . pyworks/bin/activate

既にDjangoがインストールされているものとして話を続けます。

(pyworks)$ pip install requests requests_oauthlib
(pyworks)$ cd pyworks
(pyworks)$ django-admin startproject tweetsave
(pyworks)$ cd tweetsave
(pyworks)$ python manage.py startapp myapp

ひとまず準備完了ですが、Twitter APIのキーなどは取得しておいてください。

各種基本ファイルの編集

settings.pyの最終行あたりを以下のように書き(替え)加えます。メディアに関しては書いておいたほうが後が楽だから、という感じなのですっ飛ばしても今回は問題ありません。静的ファイル部分だけ書けばいいかな、とは。

settings.py
LANGUAGE_CODE = 'ja'
TIME_ZONE = 'Asia/Tokyo'
USE_I18N = True
USE_L10N = True
USE_TZ = True


STATIC_URL = '/static/'
STATICFILES_DIRS = (
    os.path.join(BASE_DIR, 'static'),
)

MEDIA_URL = '/media/'
MEDIA_ROOT = os.path.join(BASE_DIR, 'media')

urls.pyも同様で、冗長に書いてますが「メディアファイルの取扱」を今後するかもしれないので書いておこう、くらいの感じです。

urls.py
from django.conf import settings
from django.conf.urls import url, include
from django.conf.urls.static import static
from django.contrib import admin

urlpatterns = [
    url(r'^myapp/', include('myapp.urls',namespace='myapp')),
    url(r'^admin/', admin.site.urls),
]
if settings.DEBUG:
    urlpatterns += static(settings.MEDIA_URL,document_root=settings.MEDIA_ROOT)

myapp/ にはurls.py が存在しないので新規作成します。

myapp/url.py
from django.conf.urls import url
from . import views


urlpatterns = [
    url(r'^', views.index, name='index'),
]

モデルの定義

今回はただひたすら自分のツイートをデータベースに保存しますので、シンプルです。

myapp/models.py
from django.db import models

class MyTweet(models.Model):
    tweet_words = models.CharField(max_length=140)
    created_at = models.DateTimeField(auto_now_add=True)

せっかくなので管理画面用も書いておきます。

myapp/admin.py
from django.contrib import admin
from .models import MyTweet

class MyTweetAdmin(admin.ModelAdmin):
    list_display = ('id','tweet_words','created_at')

admin.site.register(MyTweet,MyTweetAdmin)

フォームの作成

Django Formを利用しなくても全く問題ないんですが、せっかくなのでフォームを書きましょう。特にオプション的な記述はせず、ごくシンプルなフォームを生成しますので、たったこれだけ。

myapp/forms.py
from django import forms
from myapp.models import MyTweet


class TweetForm(forms.ModelForm):

    class Meta:
        model = MyTweet
        fields = ('tweet_words',)
        widgets = {
            'tweet_words': forms.Textarea()
        }

ビューを書く

自分で言うのも何ですが、凄く冗長です。

myapp/views.py
from django.http.response import HttpResponse
from django.shortcuts import render, redirect
from django import forms
from myapp.models import MyTweet
from myapp.forms import TweetForm

from requests_oauthlib import OAuth1Session
import requests
import json

C_KEY = '++++++++++++++++++++++++++++++++'
C_SECRET = '++++++++++++++++++++++++++++++++'
A_KEY = '++++++++++++++++++++++++++++++++'
A_SECRET = '++++++++++++++++++++++++++++++++'

Post_API = 'https://api.twitter.com/1.1/statuses/update.json'

tw = OAuth1Session(C_KEY,C_SECRET,A_KEY,A_SECRET)

def index(request):
    form = TweetForm(request.POST or None)

    msg = request.POST.get('tweet_words')
    url = Post_API
    params = {'status': msg,'lang': 'ja'}
    req = tw.post(url, params = params)

    if request.method == 'POST':
        if form.is_valid():
            if req.status_code == 200:
                timeline = json.loads(req.text)
                form.save()
                return redirect('myapp:index')

            else:
                contexts = {
                    'Error_message': 'API制限中',
                    }
                return render(request, 'myapp/index.html', contexts)

            return redirect('myapp:index')

    result_text = MyTweet.objects.all().order_by('-id')
    contexts = {
        'form':form,
        'result_text':result_text,
    }
    return render(request, 'myapp/index.html', contexts)

テンプレートを書く

の前に、静的ファイルのディレクトリを再確認。

スクリーンショット 2017-05-16 11.46.10.png

myapp/templates/myapp/ にテンプレートファイルを配置します。CSSやJS等の場合も同様に、
myapp/static/myapp/css~ などとして配置します。

同一プロジェクト内に複数アプリケーションを配置する場合などに、名前の競合で見つからないよ!を防ぐためです。

myapp/base.html
<!DOCTYPE html>
    <html lang="ja">
    <head>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1">
    {% load static %}
    <link rel="stylesheet" href="{% static 'myapp/css/style.css' %}" >
    <link rel="stylesheet" href="{% static 'myapp/css/bootstrap.min.css' %}">
    </head>
    <body>
        {% block body %}
        {% endblock %}
    </body>
</html>
myapp/index.html
{% extends 'myapp/base.html' %}
{% block body %}
<div class="container">
  <div class="row">
    <div class="col-md-12">
      <div class="col-md-4">
        <form action="{% url 'myapp:index' %}" method="post">
            <div class="row">
              {% for field in form %}
              <label>{{ field.label_tag }}</label>
              <label>{{ field }}</label>
              {% endfor %}
              <input type="submit" class="btn btn-primary" value="送信">
              {% csrf_token %}
            </div>
        </form>
      </div>
      <div class="col-md-8">
        {% include "myapp/result.html" %}
      </div>
    </div>
  </div>
</div>
{% endblock %}
myapp/result.html
{% block body %}
<ul class="row">
  {% for i in result_text %}
  <li class="box clearfix">
    <dl>
      <dt> {{ i.created_at }}</dt>
      <dd>{{ i.tweet_words }}</dd>
    </dl>
  </li>
  {% endfor %}
</ul>
{% endblock %}

migrations / migrate

お約束のやつをやります。

(pyworks)$ python manage.py makemigrations myapp
(pyworks)$ python manage.py migrate

必要に応じて

(pyworks)$ python manage.py createsuperuser

実行する

runserverして、実行します。

スクリーンショット 2017-05-16 11.51.18.png

なんと不毛なアプリケーションの誕生です。

2
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
3