unittest mock

patch.object(): メソッドを置き換える メソッドが外部のサーバーに対して API リクエストを行う テストではサーバー間 API が成功したものとして、状態だけ進める 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 from unittest.mock import patch from applies.utils import approve_to from base.tests.utils import RestTestCase from sourcing.models import PurchaseOrder def fake_cloudsign_post_document(self, *args, **kwargs): # サーバー間のAPIが成功したものとして承認状態を進める approve_to(self.purchase, "purchase_print") class PurchaseOrderTest(RestTestCase): @patch.object(PurchaseOrder, "cloudsign_post_document", new=fake_cloudsign_post_document) def test_create(self): # .... # response = client.post("/api/rest/sourcing/purchaseorder/", params) ... instance = PurchaseOrder.objects.get(id=response.json()["id]) self.assertEqual(instanc.purchase.purchase_status, "print")

2023年6月26日 · 1 分

django cache decorator

django: cache value decorator 1 2 from functools import wraps from django.core.cache import c 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 def cached_value(key=None, **kwargs): """ key で指定された値をキャッシュから取得して current に渡す reset=True が指定されるとキャッシュデータを使わない """ def _cache_controller(original_func): @wraps(original_func) def _cache_controlled(*args, **kw): current = None if kw.get("reset", False) else cache.get(key) lastest = original_func(*args, current=current, **kw) cache.set(key, lastest) return lastest return _cache_controlled return _cache_controller 1 2 3 4 5 class PurchaseOrder: @cached_value(key="webservice_accesstoken") def get_accesstoken(self, current=None, reset=False): return Token(self.company.credentials).update_token(current)

2023年6月22日 · 1 分

cp932

CP932 の最大バイト数を超えない長さで文字列を丸める 1 from itertools import accumulate 1 2 3 4 5 6 7 8 9 def cp932_substr(source, max_length): """CP932での最大バイト数(max_length) を超えない文字数で丸める""" if not source: return "" data = map(lambda i: len(i.encode("cp932")), source) target = filter(lambda i: i <= max_length, accumulate(data)) count = len(list(target)) return source[:count]

2023年6月21日 · 1 分

AWS Windows

AWS EC2 Windows AWS EC2 で起動した Windows Server を日本語設定にする コマンドプロンプト/英語モード・日本語モードの切り替え方法・chcp ALB のアクセスを CloudFront からだけに許可するように設定してみた Amazon VPC で Amazon CloudFront 用に AWS が管理するプレフィックスリストのサポートを開始 Work with AWS-managed prefix lists EC2Launch v2 を使用した Windows 管理者パスワードのリセット

2023年6月20日 · 1 分

at

at コマンド MacOS で at コマンドを有効化して使ってみる 手順: /System/Library/LaunchDaemons/com.apple.atrun.plist で、Disabled を false に変更 /System/Library/LaunchDaemons/com.apple.atrun.plist を再ロード 1 2 3 4 % sudo launchctl load -w /System/Library/LaunchDaemons/com.apple.atrun.plist /System/Library/LaunchDaemons/com.apple.atrun.plist: service already loaded Load failed: 37: Operation already in progress

2023年6月18日 · 1 分

ltsv

ltsv 形式 http://ltsv.org/ https://github.com/hekyou/python-ltsv pip install ltsv To process LTSV files in Python, you can use the ltsv package available on PyPI ². Here is an example of how to use it: 1 2 3 4 5 import ltsv with open('file.ltsv') as f: for record in ltsv.reader(f): print(record) This code will read the LTSV file line by line and print each record as a dictionary ¹. ...

2023年6月16日 · 1 分

ndjson

ndjson https://github.com/rhgrant10/ndjson Snowflake: CREATE FILE FORMAT 【Python】Python ~ ndjson を扱う ~ tablib は ndjson をサポートしていない pandas は ndjson を読み込める

2023年6月14日 · 1 分

django-import-export M2M

django-import-export M2M, FK django-import-export, importing ManyToMany from XLSX Widgets GroupWidget どちらでも使える: Users.groups Permission.group_set 1 2 3 4 5 6 7 8 9 10 11 12 from import_export import widgets, fields class GroupWidget(widgets.ManyToManyWidget): def clean(self, value, row=None, *args, **kwargs): if not value: return self.model.objects.none() if self.field == "name": # 存在しない場合作成する ids = value.split(self.separator) ids = filter(None, [i.strip() for i in ids]) return map(lambda i: self.model.objects.get_or_create(name=i)[0], ids) return super().clean(self, value, row=row, *args, **kwargs) ContentTypeWidget Permission.content_type など ForeingKey 定義されていると使える データは {app_label}.{model} でレンダリングされるので、取り込む時に split('.') する 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 from import_export import fields, widgets from django.contrib.contenttypes.models import ContentType class ContentTypeWidget(widgets.ForeignKeyWidget): def clean(self, value, row=None, *args, **kwargs): if value is None: return None app_label, model = value.split(".") content_type = ContentType.objects.get_by_natural_key(app_label, model) return content_type def render(self, value, obj=None): return f"{value.app_label}.{value.model}" User.groups User の Resource を定義するにあたって、groups を name で import/export するには、以下のように記述することができます。 ...

2023年6月9日 · 2 分

django グループに権限を付与

Django: 指定したグループに権限を与える 1 2 3 4 from itertools import product from django.contrib.auth.models import Permission, Group from django.contrib.contenttypes.models import ContentType from django.apps import apps 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 @main.command() @click.argument("group_name") @click.argument("model_path") @click.argument("action_suffix", nargs=-1) # view とか view_other とか @click.pass_context def group_add_perms(ctx, group_name, model_path, action_suffix): """指定したグループに権限を与える""" group = Group.objects.get(name=group_name) app_label, model_name = model_path.split(".") if app_label == "*": model_list = apps.get_models() else: model_list = list( filter( lambda i: model_name == "*" or i._meta.model_mame == model_name, apps.get_app_config(app_label).get_models(), ) ) actions = map(lambda i: i.split("_"), action_suffix) def _perm(item): model_class, actions = item content_type = ContentType.objects.get_for_model(model_class) codename = ( f"{actions[0]}_{content_type.model}_{actions[1]}" if len(actions) > 1 else f"{actions[0]}_{content_type.model}" ) return Permission.objects.filter(content_type=content_type, codename=codename).first() perms = filter(lambda i: i is not None, map(_perm, product(model_list, actions))) group.permissions.add(*perms)

2023年6月8日 · 1 分

銀行マスター

django-import-export で 銀行マスターを取り込む 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 from import_export import resources from .. import models class BankCodeResource(resources.ModelResource): class Meta: model = models.BankCode import_id_fields = ["code", "branch_code"] fields = ["code", "branch_code", "kana", "name", "branch_kana", "branch_name"] def before_import_row(self, row, row_number=None, **kwargs): for field in self._meta.fields: # ヘッダーは verbose_name に合わせている value = row.pop(self._meta.model._meta.get_field(field).verbose_name, None) if value is None: continue # コードは0埋めする if field == "code": value = str(value).zfill(4) elif field == "branch_code": value = str(value).zfill(3) row[field] = value

2023年6月8日 · 1 分