3
votes

Le routage dans Angular 7 s'exécutant dans le sous-dossier ne fonctionne pas correctement

Nous travaillons à la migration de notre application vers une nouvelle version Angular. L'ancien (Angular.JS) était sa propre application / dépôt servie par une application ASP.NET MVC .NET Framework 4.5.2 qui acheminerait chaque appel vers Home qui renverrait une vue Razor qui contenait l'application angulaire, puis démarrez-la, en acheminant éventuellement le suffixe de l'URL vers la page angulaire réelle. Par exemple, il acheminerait www.website.com/profile vers la route profile dans Angular, sans essayer d'accéder à un dossier appelé profile sur le serveur. L'intégration de notre API et de l'application Angular.JS n'est pas trop jolie mais cela a fonctionné. Le serveur a également des dossiers virtuels dans IIS pour d'autres sous-dossiers auxquels il faut accéder comme les polices, les images, les configurations, etc.

Actuellement, je travaille à faire fonctionner l'application Angular 7 avec l'application Angular.JS. Nous voulons exécuter l'application Angular 7 pour qu'elle s'exécute dans un répertoire de l'application actuelle, puis la déplacer vers sa propre application Web, car notre nouvelle application Angular n'est qu'un tas de fichiers statiques et n'a pas besoin d'être fournie avec le serveur. plus. En gros, aucune configuration ASP.NET MVC n'est nécessaire.

L'URL actuelle serait www.website.com et renverrait l'application Angular.JS. Le nouveau serait www.website.com/v2/ et renverrait l'application Angular 7. Si nous avions terminé une version v2 de la page profil , la navigation vers wwww.website.com/v2/profile devrait maintenant accéder au profil page de l'application Angular 7.

Dans IIS, l'un des dossiers virtuels est un dossier appelé dist qui mène à l'emplacement des fichiers de l'application Angular.JS. Un nouveau appelé v2 est maintenant configuré, ce qui conduit à l'emplacement des fichiers de l'application Angular 7. Un autre appelé assets mène au dossier assets de l'application Angular 7.

Maintenant, quand je navigue vers www.website.com / v2 / , Angular démarre et me dirige vers www.website.com/v2/home , qui est la route d'origine.

Le problème est que lorsque je saisis moi-même www.website.com/v2/home , l'application revient à www.website.com . et ainsi il redémarre l'application Angular.JS. Il n'y a aucune erreur ou redirection en cours. Il semble qu'il ignore simplement la partie qui suit la partie v2 / même si Angular.JS le fait très bien.

TL; DR Navigation vers www.website.com/v2 charge Angular 7, mais la navigation vers v2 / {{Anything}} entraîne le retour de l'application vers l'application Angular.JS en cours d'exécution sur www.website.com , même si {{quelque chose}} était un lien interne dans Angular 7, il naviguerait vers le {{any}} route.

Je construis le projet Angular avec la commande suivante:

ng build --configuration = dev --deploy -url = / v2 / --base-href = / v2 /

Les routes dans l'application angular 7 ressemblent à ceci:

 <rewrite>
      <rules>
        <clear />
        <rule name="Redirect Angular endpoints to MVC Home" enabled="true">
          <match url="^(profiel|timesheets|facturen|opdrachten|contact|help|gebruikers)" negate="false" />
          <conditions logicalGrouping="MatchAll" trackAllCaptures="false" />
          <action type="Rewrite" url="Home" logRewrittenUrl="false" />
        </rule>
     <!-- Some other rules that are not important are here, they redirect HTTP to HTTPS -->
     </rules>
  </rewrite>

Quelqu'un peut-il me dire comment je peux, par exemple, taper www.website.com/v2/contact dans le navigateur pour accéder à la page de contact v2, tout en rendant possible la navigation interne (donc si l'utilisateur clique sur "accéder au contact v2 p age "à l'intérieur de l'application Angular 7, il permet également d'accéder à la page de contact v2)

Edit: Informations sur Angular.JS Routerconfig et le back-end web .config ont été demandés; Je les ai fournis ci-dessous.

RouterConfig:

$routeProvider
    .when('/', {
      templateUrl: 'scripts/home/home.html',
      controller: 'HomeController',
      controllerAs: 'homeCtrl'
    })
    .when('/gebruikers', {
      templateUrl: 'scripts/users/users.html',
      controller: 'UsersController',
      controllerAs: 'usersCtrl'
    })
    .when('/profiel', {
      templateUrl: 'scripts/profile/profile.html',
      controller: 'ProfileController',
      controllerAs: 'profileCtrl'
    })
    .when('/timesheets', {
      templateUrl: 'scripts/timesheets/timesheets.html',
      controller: 'TimesheetsController',
      controllerAs: 'timesheetsCtrl',
      reloadOnSearch: false
    })
    .when('/facturen', {
      templateUrl: 'scripts/invoices/invoices.html',
      controller: 'InvoicesController',
      controllerAs: 'invoicesCtrl',
      reloadOnSearch: false
    })
    .when('/opdrachten', {
      templateUrl: 'scripts/vacancies/vacancies.html',
      controller: 'VacanciesController',
      controllerAs: 'vacanciesCtrl'
    })
    .when('/contact', {
      templateUrl: 'scripts/contact/contact.html',
      controller: 'ContactController',
      controllerAs: 'contactCtrl'
    })
    .when('/help', {
      templateUrl: 'scripts/help/help.html',
      controller: 'HelpController',
      controllerAs: 'helpCtrl'
    })
    .otherwise({
      redirectTo: '/'
    });

Règles de réécriture Web.Config IIS:

XXX


5 commentaires

incluez votre RouterConfig ici


@JohnVelasquez Merci pour votre commentaire. Je suis moi-même back-end, voulez-vous dire le RouterConfig Angular.JS? Sinon, de quelles autres informations de routage sur l'application Angular 7 avez-vous besoin? Pour l'instant, j'ai édité le message principal pour inclure le RouterConfig de l'application Angular JS; s'il vous plaît jeter un autre coup d'oeil si vous avez le temps.


Utilisez-vous ASP.NET MVC?, Si oui, incluez RouteConfig


Désolé, j'ai oublié de vous dire que je parlais d'ASP.NET


Eh bien, il a une route par défaut que vous obtenez toujours, et la valeur par défaut pour cette route est d'aller à Homecontroller , qui renvoie une vue qui, en combinaison avec la disposition de base dans razor, démarre le Angular JS app.


3 Réponses :


0
votes

Avez-vous apporté des modifications à votre fichier Web.config? Vous devez le configurer pour l'application angulaire de base (en utilisant le module UrlRewrite) Je suppose qu'il pourrait avoir besoin d'une modification pour votre cas d'utilisation ...

<rewrite>
    <rules>
      <rule name="Angular RoutesV1" stopProcessing="true">
        <match url=".*" />
        <conditions logicalGrouping="MatchAll">
          <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
          <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
        </conditions>
        <action type="Rewrite" url="/my/app/" />
      </rule>
    </rules>
  </rewrite>

Je suppose que vous aurez besoin pour ajouter une autre «règle» ici. J'espère que cela t'aides!!! (note: la réécriture est censée correspondre à votre valeur href de base de construction ng)


1 commentaires

salut! J'ai modifié mon message pour vous montrer les valeurs de la règle de réécriture IIS. À l'origine, mon dossier virtuel pour Angular 7 s'appelait distv2 pour refléter le fait que dist était pour Angular JS et distv2 pour Angular 7. Demandes reçues pour / v2 / serait alors réécrit en / distv2 / . J'ai eu quelques problèmes avec ainsi et j'ai donc renommé le dossier virtuel v2 donc je pense qu'aucune autre réécriture n'est nécessaire. Merci pour votre temps!



0
votes
  1. Supprimez vos règles de réécriture Web.Config IIS
  2. Dans votre RouteConfig changez-le de cette façon
  3. public ActionResult IndexV2()
    {
        return View();
    } 
    

    En gros, cela va capturer tous les chemins de votre route donnés avec le nom de route spécifique, le { * url} attrape tout le segment d'itinéraire quelle que soit la valeur.

    Donc, quand nous disons que l'url est;

    • localhost: 4200 / test Default
    • localhost: 4200 / v2 / test V2
    • localhost: 4200 / test / quelque chose / 2323 Default
    • localhost: 4200 / v2 / test2 / test_again / 2323 V2

    et dans votre HomeController assurez-vous d'ajouter le IndexV2

    public class RouteConfig
    {
        public static void RegisterRoutes(RouteCollection routes)
        {
            routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
    
            // don't change the arrangement, this must be executed first
            routes.MapRoute(
                    name: "V2",
                    url: "v2/{*url}",
                    defaults: new { controller = "Home", action = "IndexV2", id = UrlParameter.Optional }
                );
    
            routes.MapRoute(
                    name: "Default",
                    url: "{*url}",
                    defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
                );
            }
     }
    

4 commentaires

J'arrive là où vous voulez, mais cela signifierait que ma nouvelle application Angular doit encore être intégrée à ASP.NET MVC. Ce serait plus cool s'ils pouvaient être découplés afin que nous puissions les libérer séparément si nécessaire. Ne pourrais-je pas faire localhost: 4200 / v2 / test2 / test_again / 2323 en utilisant une règle de réécriture qui redirigerait cette URL vers localhost: 4200 / v2 puis laisser angular faire le reste (qu'est-ce que je veux)? Ensuite, je ferais presque la même chose que la solution ASP.NET MVC.


Je pense que c'est mieux comme ça pour que vous puissiez séparer le _Layout sur chaque version,


Il est! Il s'agit d'ASP.NET MVC et le JS angulaire est servi en utilisant la technique que vous décrivez. Mais l'application angular 7 n'est que des fichiers statiques, donc s'ils ne sont PAS couplés à ASP.NET MVC, nous pouvons déployer séparément le front-end et le back-end. C'est pourquoi je préférerais une solution où nous n'avons rien à faire de spécifique à ASP.NET MVc :)


hmmm je ne connais pas les règles de réécriture, c'est la seule réponse que je puisse faire pour vous



5
votes

La raison pour laquelle il serait toujours renvoyé à l'url v1 est que l'application angular 7 contenait un fichier web.config qui ressemblait à ceci:

<configuration>
    <system.webServer>
      <rewrite>
        <rules>
          <rule name="Angular" stopProcessing="true">
            <match url=".*" />
            <conditions logicalGrouping="MatchAll">
              <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
              <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
            </conditions>
            <action type="Rewrite" url="/" />
          </rule>
        </rules>
      </rewrite>
    </system.webServer>
</configuration>

Je crois que c'est par défaut pour un déploiement IIS et un membre de l'équipe peut avoir ajouté ceci. Je n'ai jamais pensé à avoir un web.config dans un projet frontal.

Fondamentalement, cette règle se charge de rediriger l'utilisateur vers l'index.html. Par exemple, www.website.com/folder amènerait normalement l'utilisateur dans un dossier appelé folder sur le serveur Web, mais ce n'est pas là que Angular s'exécute et pourrait provoquer un 404. Cette règle ramène l'utilisateur à www.website.com et laisse ensuite acheminer angular la partie dossier .

Parce que j'exécute mon application dans un sous-dossier, j'ai changé le url = "/" en url = "/ v2 /" et cela a fonctionné immédiatement!

N'oubliez pas de construire le projet avec ng build --configuration = dev --deploy-url = / v2 / --base-href = / v2 / ! L'URL de déploiement est nécessaire car les scripts / css / autres fichiers ne se trouvent pas dans le dossier racine du serveur; il se trouve dans / v2 /. La base-href est nécessaire pour le routeur; il devrait commencer à acheminer l'application sur www.website.com/v2/ et non sur www.website.com/!

Aucune autre réécriture iis des règles sont nécessaires, pas de configuration asp.net, pas de routage angulaire spécial. Juste ces étapes simples!


0 commentaires