ソフトウェア工学

システム開発ライフサイクル内で働く専門家、学者、学生向けのQ&A


1
SOA /マイクロサービス:サービス間通信で認証を処理する方法
前景 モノリシックプラットフォームから、よりサービス指向のアーキテクチャに移行しています。非常に基本的なDDDの原則を適用し、さまざまな境界のあるコンテキストにドメインを分割しています。各ドメインは配布され、Web API(REST)を介してサービスを公開します。 ビジネスの性質上、予約、サービス、顧客、製品などのサービスを提供しています。 また、主な役割が以下のことを行うIdentity Server(Thinktecture Identity Server 3ベース)をセットアップしました 認証の集中化(トークンを発行する資格情報を指定) 次のようなトークンにクレームを追加します:クライアントのスコープ(クライアントごとに要求を行うアプリケーションを意味する)、顧客識別子(顧客ごとにアプリケーションを使用する人を意味する) また、サービスへの外部アクセスを集中化するAPI Gatewayの役割も導入しました。API Gatewayは、次のような内部ドメインの深い知識を必要としない機能を提供します。 リバースプロキシ:着信要求を適切な内部サービスにルーティングします バージョン管理:API Gatewayのバージョンは、内部サービスの異なるバージョンにマップされます 認証:クライアント要求には、Identity Serverによって発行されたトークンが含まれ、API Gatewayはトークンを検証します(ユーザーが本人であることを確認してください) 調整:クライアントごとの要求数を制限する 認可 認可に関係するものは、これはAPI Gatewayではなく、内部サービス自体で管理されます。現在、主に2種類の承認を行っています。 クライアントスコープに基づく承認。例:クライアント(APIを使用する外部アプリケーション)には、予約サービスAPIエンドポイントにアクセスするためのスコープ「bookings」が必要です 顧客に基づいた承認。例:顧客(アプリケーションを使用する実在の人物)が予約の参加者である場合のみ、予約サービスからエンドポイントGET / bookingsにアクセスできます。 内部サービスで認証を処理できるようにするために、API Gatewayは、クライアント(要求を行うアプリケーション)と顧客としての情報の両方を含むトークン(内部サービスに要求をルーティングするとき)を転送するだけです人がクライアントアプリケーションにログインしている場合)。 問題の説明 これまでのところ、サービス間通信(一部のサービスは他のサービスと通信してデータを取得できます)を導入するまではこれで十分です。 質問 サービス間通信の認可にどのようにアプローチすればよいですか? 考慮されるオプション さまざまなオプションについて説明するには、次のサンプルシナリオを使用します。 予約フローを構築するために、APIにアクセスするExternalAppと呼ばれる外部アプリケーションがあります(ExternalApp はクライアントとして見ることができます) ExternalAppはBookingsサービスにアクセスする必要があるため、ExternalAppにスコープ「bookings」を付与します 内部的に(これはExternalAppに対して完全に透過的なものです)、予約サービスはサービスサービスにアクセスして、フライト、保険、レンタカーなどの予約のデフォルトサービスを取得します この問題を内部で議論する際、いくつかのオプションが表示されましたが、どのオプションが最適かはわかりません。 BookingsがServicesと通信する場合、API Gatewayから受信した元のトークンを単純に転送する必要があります(クライアントがExternalAppであることを示します) 意味:付与されるべきではないExternalAppにスコープを付与する必要がある場合があります。例:ExternalAppにはスコープ「bookings」と「services」の両方が必要な場合がありますが、「bookings」スコープのみで十分です。 BookingsがServicesと通信する場合、クライアントが(ExternalAppの代わりに)Bookingsになったことを示すトークンを転送し、Bookingsが元のクライアントExternalAppになりすましていることを示すクレームを追加します また、元のクライアントがExternalAppであるという情報を含めることにより、サービスサービスは元の呼び出し元に応じて一部のサービスを除外するなどのロジックも実行できます(たとえば、内部アプリの場合はすべての戦いを返し、外部アプリの場合は一部のみ) サービスは互いに通信すべきではありません(そのため、この質問に直面するべきではありません) ご意見をお寄せいただきありがとうございます。

3
OOPの過度の複雑化に対する用語はありますか?
1〜2年前、OOP(Java)に関する優れた記事を目にしました。この記事では、2、3行のコードからなる単純な具体的なロガーの進行と、基本的には必要に応じてこれを追加してください! 記事の終わりまでに、この単純なロガーはごみの巨大な混乱であり、元の開発者は自分自身をほとんど理解できませんでした... このタイプの過剰合併症に共通の用語はありますか?その記事(私は再び見つけられることを心から願っています)は、孤立したケースのコンセプトを素晴らしく示していますが、パターン、フレームワーク、ライブラリの過剰使用によって開発者が本質的に自分自身を結び目にプログラムしたプロジェクト全体に出くわしましたその他の問題。独自の方法で、これは、交換用に継承する従来のVB6スパゲッティアプリと同じくらい悪い(またはさらに悪い)です。 私が本当に探しているのは、面接時にこれを持ち出すことです。アーキテクチャ/事前計画の欠如でこれに陥るのがどれほど簡単かを誰かが認識し、意識しているかどうかを知りたい(そして、彼らが適切なバランスを持っているように見えるかどうかで落ち込む)が、それは本当に何かではない私は多くの情報を見つけることができます。

6
makefileに「インストール」ターゲットが必要なのはなぜですか?
CとC ++の世界から来たほとんどのビルドシステムには、installターゲット、特にMakefiles(たとえばGNUが推奨する場所)またはCMakeがあります。このターゲットは、オペレーティングシステム(C:\Program Files\Windowsなど)のランタイムファイル(実行可能ファイル、ライブラリなど)をコピーします。 私にとっては、プログラムをインストールすることはビルドシステムの責任ではないため(実際にはオペレーティングシステム/パッケージマネージャーの責任です)、これは非常にハッキリしています。また、ビルドシステムまたはビルドスクリプトは、環境変数、レジストリ変数、シンボリックリンク、権限などを使用して、インストールされたプログラムの構成を認識している必要があります。 せいぜい、ビルドシステムにはrelease、インストール可能なプログラム(.debまたはなど.msi)を出力するターゲットがあり、そのプログラムをインストールするようオペレーティングシステムに親切に依頼する必要があります。また、ユーザーはを入力せずにアンインストールできmake uninstallます。 だから、私の質問:ビルドシステムは通常、installターゲットを持つことを推奨するのはなぜですか?

2
依存性注入を使用すると、ソフトウェアエンジニアリングの成果が向上するという証拠はありますか?
その人気にもかかわらず、依存性注入(および/またはDIコンテナーの使用)が、バグ数の削減、保守性の向上、または実際のソフトウェアプロジェクトの開発速度の向上に役立つことを示す経験的証拠はありますか?

3
WebアプリケーションでRPCのようなメカニズムの代わりにRESTが一般的に使用されるのはなぜですか?
私はごく最近、少なくとも私が知っている典型的なWebアプリケーションフレームワークと比較して、Webアプリケーションにかなり珍しいカスタムフレームワークを使用している会社で働き始めました。RESTful Webサービスの代わりに、RPCメカニズムを使用してサーバーと通信します。 サーバーとの通信は単純な関数呼び出しのように見えますが、関数はクライアントではなくサーバー上で実行されます。サーバー側には、クライアントが呼び出すことができる機能を定義する方法があります。これをhttpリクエストに変換する方法の詳細は完全に抽象化されています。 私は今これを短い時間だけ使用しましたが、それはかなり便利なようです。しかし、私はこのアプローチのどのような欠点が欠けているのか疑問に思っています。他の誰もが違うやり方をしているように見えますが、これは通常、前者に比べてはるかに高い確率で、私が愚かで素晴らしいことをしているかもしれないというサインです。

5
RESTful APIは、物がないことを表します
人が霊獣を選択したかどうかを識別するAPIを想像してください。彼らはゼロまたは1つのスピリット動物しか持つことができません。 現在: /person/{id}/selectedSpiritAnimal 動物が選択されると、http 200が返され、 {selectedAnimal:mole} ただし、選択がない場合は、http 404が返されます。 これは、HTTPエラーとして、まだスピリット動物を選択していない有効なドメインの懸念を表しているため、スピリット動物を不幸にします。 さらに、ビジネスとして-erm Sprit-Animal-Hampers-R-us-誰かに選択がないときを知りたいので、それらを促すことができます。 ここでより良い応答は何ですか: HTTP 200および {selectedAnimal:null} またはさらに明示的に HTTP 200および {selectedAnimal:null, spiritAnimalSelected: false} それとも、404を返す方が良いでしょうか?this image has not yet been uploadedオンラインで画像を表示するときは404によく似ているのでthis person has not selected a spirit animal、 この質問は重複として提案されていますが、その質問は、URLが表す変更を許可しないようにアプリケーションが構成されている場合に要求される有効なURLに対処します。 一方、ここでは、リソースが存在しないことが意味のあるリソースをどのように表すかを検討しています。つまり、クライアントがURLを要求することは有効であり、応答は、モノの不在を表すリソースを正常に要求したということです。 だから、これは「ビジネスロジック」ではなく、物の不在が意味を持っている状況です(404がまだ正しいと主張している多くの同僚がいるかもしれません)が、それをどのようにマッピングするのかわかりませんスペック 答えを選ぶのは非常に難しい。ここでの会話と職場で進行中の会話について、何度も考えを変えました。 ここで落ち着いているのは、仕様書には4xxはクライアントが間違っているときだと言われているということです。この例では、クライアントはselectedSpiritAnimal URLからの応答を予期するように指示されているため、エラーはありません。 私の同僚の間のコンセンサスは、これは悪いAPI設計の症状であるということです おそらく/ person / {id}をリクエストし、その人のリンク関係のセットを返す方が良いでしょう...もし/ selectedSpiritAnimalリンクが与えられていない場合(人に選択がない場合)とにかくそれを呼び出すと、404が理にかなっています。または、クライアントがデータのサブセットを要求しない限り、部分応答を実装し、/ person / {id}がより完全なドキュメントを返すようにすること
18 rest 

4
プログラマーへの参照透過性の利点は何ですか?
プログラミングにおいて、参照の透明性の利点は何ですか? RTは、機能的パラダイムと命令型パラダイムの大きな違いの1つであり、機能的パラダイムの支持者が命令型パラダイムに対する明確な利点としてよく使用します。しかし、彼らの努力のすべてにおいて、これらの支持者は、それがプログラマーとしての私にとってなぜ利益であるかを決して説明しません。 確かに、彼らはそれがどのように「純粋」で「エレガント」であるかについて学問的な説明をしますが、それほど「純粋でない」コードよりもそれをどのように改善しますか?毎日のプログラミングでどのようなメリットがありますか? 注: これは、参照透過性とは何ですか? 後者はRTとは何かというトピックに対処しますが、この質問はその利点を扱います(それほど直感的ではないかもしれません)。

7
制御フローによって冗長になる状況では、「else」を使用する必要がありますか?
次の例のようなコードに出くわすことがあります(この関数の機能はこの質問の範囲外です)。 function doSomething(value) { if (check1(value)) { return -1; } else if (check2(value)) { return value; } else { return false; } } あなたが見ることができるように、if、else ifおよびelseステートメントは、と組み合わせて使用されているreturn声明。これはカジュアルなオブザーバーにはかなり直感的に思えますが、else-s を削除し、次のようにコードを簡略化する方が(ソフトウェア開発者の観点から)よりエレガントになると思います。 function doSomething(value) { if (check1(value)) { return -1; } if (check2(value)) { return value; } return false; } これは理にかなっています。return(同じスコープ内の)ステートメントに続くすべてが実行されることはないため、上記のコードは意味的に最初の例と等しくなります。 上記のうち、優れたコーディングプラクティスに適しているものはどれですか?コードの可読性に関して、どちらの方法にも欠点はありますか? 編集:参照として提供されたこの質問で、重複した提案が行われました。私の質問は別のトピックに関係していると思います。他の質問で提示されたような重複したステートメントを避けることを求めていないからです。どちらの質問も、わずかに異なる方法ではありますが、繰り返しを減らすことを目指しています。

5
LEFT JOINよりRIGHT JOINを好む理由
私が正しく理解していれば、すべてRIGHT JOIN: SELECT Persons.*, Orders.* FROM Orders RIGHT JOIN Persons ON Orders.PersonID = Persons.ID 次のように表現できますLEFT JOIN。 SELECT Persons.*, Orders.* FROM Persons LEFT JOIN Orders ON Persons.ID = Orders.PersonID 私の個人的な意見は、声明の意図は次のとおりです。 最初に Persons 次にPersons、必要に応じてを展開/繰り返して、Orders はPersons LEFT JOIN Orders、逆の順序よりもの順序で表されOrders RIGHT JOIN Personsます(RIGHT JOIN結果として私は決して使用しません)。 RIGHT JOINが望ましい状況はありますか?または、できないRIGHT JOINことを実行できるユースケースはありますLEFT JOINか?

7
DevOpsは、開発者がインフラストラクチャとリリースに責任を持つようになったことを意味しますが、この変更の背後にある要因は何ですか?
DevOpsは、開発者がインフラストラクチャとリリースに責任を持つようになったことを意味しますが、この変更の背後にある要因は何ですか? 私は自分のカードをテーブルに置きます。私は開発者であり、「DevOps」と非文化の両方で働いていました。インフラストラクチャとリリース、QA、および関連するセレモニーを心配することは、優れたコードを書くことに対する大きな注意散漫です。 しかし、業界はこの方向に向かっています。その理由は何ですか?役割の専門化の「古い」モデルはどのような問題を引き起こしましたか?
18 process  devops 

5
コードが「間違っている」必要がある場合、レビュアーとして何をすべきですか?
私は、数ヶ月前に必須のコードレビューが導入された、設計が不十分でオーバーエンジニアリングされたプロジェクトで働いています。 新しい機能を実装するコードのかなりの部分をレビューするように頼まれました。コードベースの他の部分と同じ欠陥があります。私は、これらの欠陥が新しいコードに忍び込むことを大いに理解しています。ひどく設計されたクラスから継承するか、互換性を保持しながらひどく設計されたインターフェイスを実装する必要があるため、コードベースの半分を書き直さずに、はるかに優れたソリューションを提供することはできません。しかし、エンジニアリングの観点からは、すでに壊れているコードベースに対して、それをさらに壊していることは役に立たないと思います。私がレビューしているコードは間違いなく悪いですが、機能を実装する場合はそうでなければなりません。 この特定のレビューに関して、どのように振る舞うべきですか?誠実さを維持し、建設的であり続ける方法はありますか? この文脈でのコードレビューの境界について尋ねていることに注意してください。この問題は組織や仕事の文化などの他の要因によって引き起こされることは承知していますが、私が知りたいのはレビュー自体の処理方法です。

3
静的分析の型に代わるものはありますか?
プログラミング言語での静的型付けは、コンパイル時に特定の保証を強制するのに役立ちますが、型はこの仕事のための唯一のツールですか?不変条件を指定する他の方法はありますか? たとえば、言語または環境は、配列の長さ、または関数への入力間の関係に関する保証を実施するのに役立ちます。型システム以外では、このようなことは聞いたことがありません。 関連することは、静的分析を行うための非宣言的な方法があるかどうかです(ほとんどの場合、型は宣言的です)。

3
計算を行列乗算として表現すると、なぜ高速になるのですか?
TensorFlowを使用した GoogleのMNistチュートリアルでは、1つのステップが行列にベクトルを掛けることに相当する計算が示されています。Googleは最初に、計算の実行に使用される各数値の乗算と加算が完全に書き出された図を示します。次に、代わりに行列乗算として表されている図を示します。このバージョンの計算はより高速であるか、少なくとも高速であると主張しています。 それを方程式として書くと、次のようになります。 この手順を「ベクトル化」して、行列乗算とベクトル加算に変換できます。これは計算効率に役立ちます。(それはまた、考えるのに便利な方法です。) このような方程式は通常、機械学習の実践者によって行列乗算形式で記述されていることを知っています。もちろん、コードの簡潔さや数学の理解の観点からそうすることの利点を理解できます。私が理解していないのは、長文形式から行列形式への変換が「計算効率に役立つ」というGoogleの主張です 計算を行列乗算として表現することにより、いつ、なぜ、どのようにソフトウェアのパフォーマンスを向上させることができますか?人間として、2番目の(マトリックスベースの)イメージでマトリックスの乗算を自分で計算する場合、最初の(スカラー)イメージに示されている個別の計算を順番に実行することでそれを行います。私にとって、それらは同じ計算シーケンスの2つの表記法にすぎません。なぜ私のコンピューターと違うのですか?なぜコンピューターはスカラー計算よりも速くマトリックス計算を実行できるのでしょうか?

5
どのレイヤーに検証を配置する必要がありますか?
Spring Bootを使用してRest APIを作成し、Hibernate Validationを使用してリクエスト入力を検証しています。 しかし、他の種類の検証も必要です。たとえば、更新データを確認する必要がある場合、会社IDが存在しない場合は、カスタム例外をスローする必要があります。 この検証は、サービス層またはコントローラー層に配置する必要がありますか? サービス層: public Company update(Company entity) { if (entity.getId() == null || repository.findOne(entity.getId()) == null) { throw new ResourceNotFoundException("can not update un existence data with id : " + entity.getId()); } return repository.saveAndFlush(entity); } コントローラー層: public HttpEntity<CompanyResource> update(@Valid @RequestBody Company companyRequest) { Company company = …

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.