如何在使用石墨烯和烧瓶构建的graphql端点上发出json请求



我有一个烧瓶应用程序,我正在使用石墨烯构建一些graphql端点。以下代码片段用于构建metadata_by_config查询。

engine = create_engine('postgres_url', convert_unicode=True)
db_session = scoped_session(sessionmaker(autocommit=False, autoflush=False, bind=engine))
Base = declarative_base()
Base.query = db_session.query_property()
class MetadataModel(Base):
__tablename__ = "metadata"
id = Column(Integer, primary_key=True, autoincrement=True)
created = Column(DateTime, nullable=False)
config = Column(String(255), unique=False, nullable=False)
def __init__(self, config, description):
self.created = datetime.datetime.now()
self.config = config

class Metadata(SQLAlchemyObjectType):
class Meta:
model = MetadataModel
interfaces = (relay.Node, )

# Query
class QueryID(graphene.ObjectType):
node = relay.Node.Field()
metadata_by_id = graphene.List(Metadata, id=graphene.String())
@staticmethod
def resolve_metadata_by_id(parent, info, **args):
q = args.get('id')
metadata_query = Metadata.get_query(info)
return metadata_query.filter(MetadataModel.id == q).all()
# schema
schema_id = graphene.Schema(query=QueryID, types=[Metadata])
app = Flask(__name__)
app.debug = True

app.add_url_rule(
'/graphql-id',
view_func=GraphQLView.as_view(
'graphql-id',
schema=schema_id,
graphiql=True
)
)

if __name__ == '__main__':
app.run(host='0.0.0.0')

当我用图形查询语言进行请求时,这很好,如下所示:

q = """
{
metadataById (id: 1){
id
created
config
}
}
"""
resp = requests.post("http://localhost:5000/graphql-id", params={'query': q})
print(resp.text)

然而,由于它是石墨烯,所以没有单独的graphql服务器(代码优先的方法(。因此,我试图弄清楚是否有一种方法可以从最终用户那里抽象出图形查询语言知识,而用户不需要知道gql或后端实现的详细信息。用户应该能够像requests.post("http://localhost:5000/graphql-id", json={'id': 1})一样发出JSON请求,就好像它是一个休息的API,然后服务器解析JSON并准备适当的查询,可能是在解析器方法中。

我想使用重定向(暴露另一个与graphql端点对话的端点(来处理这个场景,并通过在app.before_request上添加一个条件(如下所示(使graphql-config端点只能在本地主机上访问:

@app.before_request
def before_request():
if request.remote_addr != "127.0.0.1" and request.path == "/v1/graphql-config":
abort(403)

然而,这似乎有点棘手和脆弱,有什么明确或更好的方法来处理这件事吗?

Ahh我没有意识到我们实际上可以执行我们的模式,所以我们不需要使用flask-graphqlGraphQLView来创建端点。因此,我实现了我的端点如下:

@app.route('/getMetadata', methods=['GET'])
def getMetadata():
data = request.get_json()
MetaId = data["id"]
query = '{ metadataById (id: ' + f""{metaId}"" '){id created config}}'
result = schema_id.execute(query)
return flask.make_response(result, 200)

在这里,最终用户只需发出JSON请求,不需要知道graphql查询。

最新更新