2017-10-10 11 views
1

Je suis actuellement le UI5 tutorial et je suis bloqué sur step 27: Configuration du serveur maquette. Le problème est la configuration du serveur fictif rootUri. J'utilise le Northwind OData service selon le tutoriel et ai configuré un dataSource pour Factures dans le manifest.json.UI5 Mock Server avec des données locales: "rootUri" ne fonctionne pas

Maintenant, pour utiliser les données de simulation locales au lieu du service en ligne, j'ai créé les fichiers nécessaires comme indiqué par le tutoriel. Lorsque j'exécute ensuite le mockServer.html, le serveur ne redirige pas la demande de service vers les données de simulation locales, mais effectue la demande et échoue en raison de problèmes de sécurité Web.

Si je le rootUri suivant, le serveur simulé ne redirige pas et la demande de service échoue:

// Snippet from mockserver.js 
var oMockServer = new MockServer({ 
    rootUri: "/destinations/northwind/V2/Northwind/Northwind.svc/" 
}); 

Failed to load https://services.odata.org/V2/Northwind/Northwind.svc/ $metadata?sap-language=DE: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin ' https://webidetesting9515320-s0015250556trial.dispatcher.hanatrial.ondemand.com ' is therefore not allowed access. The response had HTTP status code 501.

Another question on Stackoverflow montre le serveur simulé en utilisant une racine-uri « joker », mais échoue aussi:

// Snippet from mockserver.js 
var oMockServer = new MockServer({ 
    rootUri: "/" 
}); 

la seule façon que je peux faire le travail de configuration du serveur est simulé à utiliser la même URL exacte que le rootUri que je s écrit dans le manifest.json comme l'URI de la source de données Je veux railler:

// Snippet from mockserver.js 
var oMockServer = new MockServer({ 
    rootUri: "https://services.odata.org/V2/Northwind/Northwind.svc/" 
}); 

Le code ci-dessus fonctionne, mais le Web IDE indique que cela est une mauvaise pratique:

error: Fiori Architectural Guidelines: ESLint(sap-no-hardcoded-url): Hardcoded (non relative) URL found. (img)

Mon question est maintenant: Comment puis-je faire fonctionner le serveur fictif de la manière voulue avec un relatif rootUri?


webapp/manifest.json (extrait)

{ 
    "_version": "1.1.0", 
    "sap.app": { 
    "_version": "1.1.0", 
    "id": "sap.ui.tutorial.walkthrough", 
    "type": "application", 
    "i18n": "i18n/i18n.properties", 
    "title": "{{appTitle}}", 
    "description": "{{appDescription}}", 
    "applicationVersion": { 
     "version": "1.0.0" 
    }, 
    "dataSources": { 
     "invoiceRemote": { 
     "uri": "https://services.odata.org/V2/Northwind/Northwind.svc/", 
     "type": "OData", 
     "settings": { 
      "odataVersion": "2.0" 
     } 
     } 
    } 
    }, 
... 

webapp/test/mockServer.html

<!DOCTYPE html> 
<html> 
    <head> 
     <meta http-equiv="X-UA-Compatible" content="IE=edge"> 
     <meta charset="utf-8"> 
     <title>Hello World App - Test Page</title> 
     <script src="/resources/sap-ui-core.js" 
       id="sap-ui-bootstrap" 
       data-sap-ui-theme="sap_belize" 
       data-sap-ui-libs="sap.m" 
       data-sap-ui-compatVersion="edge" 
       data-sap-ui-preload="async" 
       data-sap-ui-resourceroots='{ 
        "sap.ui.tutorial.walkthrough": "../" 
       }'></script> 

     <script type="text/javascript"> 
      sap.ui.getCore().attachInit(function() { 
       sap.ui.require([ 
        "sap/ui/tutorial/walkthrough/localService/mockserver", 
        "sap/m/Shell", 
        "sap/ui/core/ComponentContainer" 
       ], function(mockserver, Shell, ComponentContainer) { 
        mockserver.init(); 

        new Shell({ 
         app: new ComponentContainer({ 
          name: "sap.ui.tutorial.walkthrough", 
          height: "100%" 
         }) 
        }).placeAt("content") 
       }); 
      }); 
     </script> 
    </head> 
    <body class="sapUiBody" id="content"> 
    </body> 
</html> 

webapp/LocalService/mockserver.js

sap.ui.define([ 
    "sap/ui/core/util/MockServer" 
], function (MockServer) { 
    "use strict"; 

    return { 
     init: function() { 
      // create 
      var oMockServer = new MockServer({ 
       rootUri: "https://services.odata.org/V2/Northwind/Northwind.svc/" 
      }); 
      var oUriParameters = jQuery.sap.getUriParameters(); 
      // configure 
      MockServer.config({ 
       autoRespond: true, 
       autoRespondAfter: oUriParameters.get("serverDelay") || 1000 
      }); 
      // simulate 
      var sPath = jQuery.sap.getModulePath("sap.ui.tutorial.walkthrough.localService"); 
      oMockServer.simulate(sPath + "/metadata.xml", sPath + "/mockdata"); 
      // start 
      oMockServer.start(); 
     } 
    }; 
}); 

webapp/LocalService/metadata.xml

<edmx:Edmx Version="1.0" xmlns:edmx="http://schemas.microsoft.com/ado/2007/06/edmx"> 
    <edmx:DataServices m:DataServiceVersion="1.0" m:MaxDataServiceVersion="3.0" 
         xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata"> 
     <Schema Namespace="NorthwindModel" xmlns="http://schemas.microsoft.com/ado/2008/09/edm"> 
      <EntityType Name="Invoice"> 
       <Key> 
        <PropertyRef Name="ProductName"/> 
        <PropertyRef Name="Quantity"/> 
        <PropertyRef Name="ShipperName"/> 
       </Key> 
       <Property Name="ShipperName" Type="Edm.String" Nullable="false" MaxLength="40" FixedLength="false" 
          Unicode="true"/> 
       <Property Name="ProductName" Type="Edm.String" Nullable="false" MaxLength="40" FixedLength="false" 
          Unicode="true"/> 
       <Property Name="Quantity" Type="Edm.Int16" Nullable="false"/> 
       <Property Name="ExtendedPrice" Type="Edm.Decimal" Precision="19" Scale="4"/> 
      </EntityType> 
     </Schema> 
     <Schema Namespace="ODataWebV2.Northwind.Model" xmlns="http://schemas.microsoft.com/ado/2008/09/edm"> 
      <EntityContainer Name="NorthwindEntities" m:IsDefaultEntityContainer="true" p6:LazyLoadingEnabled="true" 
          xmlns:p6="http://schemas.microsoft.com/ado/2009/02/edm/annotation"> 
       <EntitySet Name="Invoices" EntityType="NorthwindModel.Invoice"/> 
      </EntityContainer> 
     </Schema> 
    </edmx:DataServices> 
</edmx:Edmx> 
+0

Veuillez vérifier l'étape 26 dans le didacticiel. Il y a une section "Note" et "Attention" concernant l'accès au service OData distant. –

+0

Les cases "Note" et "Attention" du tutoriel traitent des effets de la gestion CORS par le navigateur. Si je comprends bien, nous créons le mockserver dans le seul but d'utiliser des données locales au lieu de distantes - CORS n'est donc plus un problème et les cases "Note" et "Attention" ne sont pas pertinentes. Est-ce que j'ai râté quelque chose? –

+0

S'il vous plaît essayez avec les fichiers exactement comme téléchargé de la "Walkthrough - Étape 27". Ensuite, l'application devrait fonctionner en mode simulé exactement comme téléchargé. –

Répondre

1

Il y a quelques règles à surveiller en ce qui concerne la définition du rootUri pour le serveur simulé.

Le rootUri

  • doit être relatif
  • doit se terminer par une barre oblique ("/")
  • doit correspondre à l'URI qui est attribué à votre modèle.

Il est mentionné dans le step 27:

(The rootUri) matches the URL of our data source in the descriptor file.

En plus dans le sujet Mock Server: Frequently Asked Questions:

The root URI has to be relative and requires a trailing '/'. It also needs to match the URI set in OData/JSON models or simple XHR calls in order for the mock server to intercept them.


Il n'a pas d'importance comment votre rootUri est défini comme tant qu'il remplit ces trois exigences mentionnées ci-dessus. C'est pourquoi certains URI arbitraires comme rootUri: "/" fonctionnent également mais seulement si le uri dans la source de données est identique.

Dans votre cas, en changeant la valeur rootUri comme ceci ci-dessous devrait rendre le serveur maquette en marche:

var oMockServer = new MockServer({ 
    rootUri: "/destinations/northwind/V2/Northwind/Northwind.svc/" 
}); 

Et dans votre descripteur d'application respectivement ..:

"dataSources": { 
    "invoiceRemote": { 
    "uri": "/destinations/northwind/V2/Northwind/Northwind.svc/", 
    "type": "OData", 
    "settings": { 
     "odataVersion": "2.0" 
    } 
    } 
} 
+0

Désolé, je n'ai pas trouvé le temps de vérifier votre réponse jusqu'à maintenant. Donc, fondamentalement, cela fait fonctionner le mockserver comme prévu et je marquerai votre réponse comme acceptée. ** MAIS ** la version non-mockserver ne peut plus fonctionner. 'Impossible de charger la ressource: le serveur a répondu avec un statut de 404 (trouvé) « /destinations/northwind/V2/Northwind/Northwind.svc/ »' Je sais, cela est probablement lié au service de ne pas être enregistré sur le serveur. Mais je serais très intéressé de voir le mockserver fonctionner dans des conditions "réelles" avec des services réels et existants en dehors du serveur. –

+0

@DanielKneip Salut, pas de problème. Merci d'avoir accepté ma réponse. La raison de 404 est que le chemin est inconnu. Pour que le chemin fonctionne dans un scénario non mockserver, vous devez soit enregistrer une [destination dans SAP Cloud Platform] correspondante (https://ui5.sap.com/#/topic/3a16c7a2f1e944deb000db49e5ece6be) et modifier [neo-app.json ] (https://help.sap.com/viewer/65de2977205c403bbc107264b8eccf4b/Cloud/en-US/aed1ffa3f3e741b3a4573c9e475aa2a4.html) dans votre projet en conséquence ** ou ** vous remplacez le chemin avec 'https: //cors-anywhere.herokuapp .com/services.odata.org/V2/Northwind/Northwind.svc/'partout. – boghyon

+0

@DanielKneip À propos de la première approche I [mentionné ci-dessus] (https://stackoverflow.com/questions/46664672/ui5-mock-server-with-local-data-rooturi-not-working/47181847#comment82587427_47181847); cette rubrique explique également comment éditer neo-app.json: https://ui5.sap.com/#/topic/672301f4f47640a8b2bc817d2ce0f512.html – boghyon

0

Quelques détails du chapitre 27 du tutoriel sont assez trompeurs.

  1. Le rootUri du MockServer doit correspondre au paramètre uri de la source de données dans manifest.json.

  2. Au lieu de changer les uri de DataSource à la (mauvaise) rootUri de MockServer donné dans le tutoriel, vous devriez réellement changer rootUri de MockServer à l'URI de la source externe. En webapp/localService/mockserver.js utiliser ce bloc corrigé:

    var oMockServer = new MockServer({ 
         rootUri: "https://services.odata.org/V2/Northwind/Northwind.svc/" 
        }); 
    

Cela va créer un MockServer qui intercepte tous les appels à cette URI externe et y répond localement. Et avec cette construction, il est effectivement possible d'accéder au MockServer via /webapp/test/mockServer.html et le serveur de données en direct via /webapp/index.html.

Astuce:
Vous aurez très probablement encore des difficultés à accéder à la source de données (externe) d'origine en utilisant /webapp/index.html en raison de mêmes restrictions politiques d'origine (SOP). Avec Google Chrome, cela peut être bien résolu en exécutant une seconde (!) Instance du navigateur sans SOP. Cela est possible en parallèle avec d'autres fenêtres de navigateur ouvertes de l'instance standard WITH SOP, de sorte que vous n'avez pas besoin de fermer toutes vos fenêtres de navigateur ouvertes. Voir this answer pour plus de détails.

+0

Je ne vois aucune erreur dans l'étape du tutoriel. La Procédure pas à pas suppose que le projet est construit sur Web IDE/SCP dans lequel vous pouvez [définir des destinations] (https://stackoverflow.com/questions/46664672/ui5-mock-server-with-local-data-rooturi-not -working/47181847 # comment82587427_47181847). Et l'auteur de la question mentionne également qu'il utilise Web IDE. Donc dans ce cas, l'URI '/ destinations/northwind/V2/Northwind/Northwind.svc /' est totalement valide et fonctionne même sans démarrer le faux serveur. Pas besoin de contourner SOP. – boghyon

+0

@boghyon: Corrigez-moi, si je me trompe. J'ai suivi moi-même le Walkthrough et j'ai été pris au piège au même chapitre. L'enregistrement d'une destination n'est expliqué nulle part dans le tutoriel. Le chapitre 27 affirme simplement qu'avec les changements donnés, le serveur mockserver et le serveur de vie peuvent être utilisés alternativement en utilisant les deux URL d'entrée différentes. Une destination n'est définie/enregistrée nulle part. – Jpsy

+0

Il est correct que la procédure pas à pas elle-même ne dit pas beaucoup sur l'enregistrement de la destination, cependant, il est incorrect qu'il y ait une erreur depuis [la même étape] (https://ui5.sap.com/#/topic/bae9d90d2e9c4206889368f04edab508) mentions que "L'URI [...] pointe vers notre destination configurée pour SAP Web IDE (voir l'étape précédente) Nous supposons que cette destination est disponible." L'étape précédente contient alors un lien vers [this] (https://ui5.sap.com/#/topic/5bb388fc289d44dca886c8fa25da466e) qui pointe vers [this] (https://ui5.sap.com/#/topic/3a16c7a2f1e944deb000db49e5ece6be) additivement. Tout est là – boghyon