Problem leży w cast(Unicode)
Postgresql json
kolumna. Po prostu przesyła plik json
do typu tekstu podstawowego Unicode
SQLAlchemy , w przypadku Postgresql VARCHAR
. Innymi słowy, zamiast wyodrębniania treści tekstowej tworzy reprezentację ciągu znaków JSON. Jeśli dane wejściowe zawierały kody Unicode ze znakami ucieczki, są one wyprowadzane tak, jak w tym przypadku. Biorąc pod uwagę prosty Test
model z json
kolumna dane :
In [7]: t = Test(data={'summary': 'Tämä on summary.'})
In [8]: session.add(t)
In [9]: session.commit()
In [11]: session.query(Test.data['summary'].cast(Unicode)).scalar()
Out[11]: '"T\\u00e4m\\u00e4 on summary."'
Powinno być oczywiste, dlaczego dopasowanie z niezmienionymi znakami Unicode zakończy się niepowodzeniem. Prawidłowym sposobem wyodrębnienia treści tekstowej, z zachowaniem unikodu ucieczki, jest użycie astext
, który używa ->>
operator
w Postgresql:
In [13]: session.query(Test.data['summary'].astext).scalar()
Out[13]: 'Tämä on summary.'
Cytując dokumentację funkcji JSON i operatorów:
Więc w twoim przypadku:
Message.query.\
filter(Message.content['summary'].astext.match(term))
Pamiętaj, że dotyczy to tylko json
wpisz, a nie jsonb
, ponieważ json
type nie konwertuje znaków ucieczki Unicode na wejściu. jsonb
z drugiej strony konwertuje wszystkie ucieczki Unicode na równoważne ASCII lub UTF-8 znaki do przechowywania
. Jeśli nasz Test
model zawierał drugą kolumnę data2 jsonb
, z dokładnie tymi samymi danymi wejściowymi, wynik byłby następujący:
In [11]: session.query(Test.data['summary'].cast(Unicode),
...: Test.data2['summary'].cast(Unicode)).first()
Out[11]: ('"T\\u00e4m\\u00e4 on summary."', '"Tämä on summary"')
Mimo to powinieneś używać astext
, jeśli chcesz tekst zamiast ciągu reprezentującego JSON.