4

以下のURL形式で2つの異なるアクションを呼び出すことができるルート(または2つ)を作成しようとしています。

mydomain.com/profile
mydomain.com/profile/1234/something

2番目の形式の場合、1234は必須の整数値である必要somethingがあり、オプションの文字列である必要があります。最初の形式は、リテラルルートを使用することで簡単になります。2番目の形式のセグメント子ルートを追加できると思いましたが、機能させることができません。最初のフォーマットを省略し、セグメントルートで2番目のフォーマットのみを実行しようとしましたが、それでも成功しませんでした。

これが私が試したことです:

'profile' => array(
    'type' => 'Zend\Mvc\Router\Http\Literal',
    'options' => array(
        'route' => '/profile',
        'defaults' => array(
            'controller' => 'User\Controller\User',
            'action' => 'profile'
        )
    ),
    'child_routes' => array(
        'profile_view' => array(
            'type' => 'Zend\Mvc\Router\Http\Segment',
            'options' => array(
                'route' => '/:code[/:username]',
                'constraints' => array(
                    'code' => '[0-9]*',
                    'username' => '[a-zA-Z0-9_-]*'
                ),
                'defaults' => array(
                    'controller' => 'User\Controller\User',
                    'action' => 'view_profile'
                )
            )
        )
    )
)

の場合mydomain.com/profile、次のエラーが発生します。

Fatal error: Uncaught exception 'Zend\View\Exception\RuntimeException' with message 'No RouteMatch instance provided'

の場合mydomain.com/1234/something、次のエラーが発生します。

Fatal error: Uncaught exception 'Zend\Mvc\Router\Exception\InvalidArgumentException' with message 'Missing parameter "code"'

マニュアルには次のように記載されています。

セグメントがオプションの場合は、角かっこで囲む必要があります。例として、「/:foo [/:bar]」は「/」の後にテキストが続くものと一致し、それをキー「foo」に割り当てます。追加の「/」文字が見つかった場合、最後の文字に続くテキストがキー「バー」に割り当てられます。

それは私がしていることとまったく同じではありませんか?制約をコメントアウトしても、上記のエラーは同じままです。

ここで何が欠けていますか?前もって感謝します。

4

5 に答える 5

5

My solution: Set the default for your optional parameter to empty string

I ran into a similar problem, I solved it by setting the default value for the optional parameter (in your case "username" to an empty string ""; My solution:

'users' => array(
    'type' => 'segment',
    'options' => array(
        'route' => '/users[/:user_id]',
        'constraints' => array(
            'user_id' => '[0-9]*',
        ),
        'defaults' => array(
            'controller' => 'My\Controller\User',
            'user_id' => ""
        )
    ),
于 2013-09-17T12:20:20.630 に答える
4

I played around with it some more. After debugging, I still couldn't figure it out. I tried to add a default value to the code parameter and that seemed to do the trick. Why on Earth that works and how it makes sense, I have no idea. To me it shouldn't matter if I have a default value specified or not if I have provided a value in the URL for the parameter in the URL. Nevertheless, apparently it does matter - or at least in this case it did.

Here is the working code. I also updated the regular expression for the code parameter.

'profile' => array(
    'type' => 'Zend\Mvc\Router\Http\Literal',
    'options' => array(
        'route' => '/profile',
        'defaults' => array(
            'controller' => 'User\Controller\User',
            'action'     => 'profile',
        ),
    ),
    'may_terminate' => true,
    'child_routes' => array(
        'view' => array(
            'type' => 'Zend\Mvc\Router\Http\Segment',
            'options' => array(
                'route' => '/:code[/:username]',
                'constraints' => array(
                    'code' => '\d+',
                    'username' => '[a-zA-Z0-9_-]*',
                ),
                'defaults' => array(
                    'controller' => 'User\Controller\User',
                    'action' => 'viewProfile',
                    'code' => 0,
                ),
            ),
        ),
    ),
),
于 2013-02-25T20:12:17.287 に答える
1

あなたが得る2番目の例外はMissing parameter "code"、一致しない、組み立てることから来ます。これは、ルートをアセンブルするときにコードを指定しなかったことを意味しますprofile/profile_view

ちなみに、child_routesの前に親ルートの名前を付ける必要はありません。子ルートを「ビュー」と呼び、としてアセンブルしprofile/viewます。

于 2013-02-25T04:38:31.930 に答える
0

I believe you are missing the may_terminate option, like so:

'profile' => array(
    'type' => 'Zend\Mvc\Router\Http\Literal',
    'options' => array(
        'route' => '/profile',
        'defaults' => array(
            'controller' => 'User\Controller\User',
            'action' => 'profile'
        )
    ),
    'may_terminate' => true,
    'child_routes' => array(
    ...
于 2013-02-23T22:33:26.697 に答える
0

Two reasons this occurs according to Bittarman. The main reason, he says, is:

<Bittarman> ezio, that looks like what happens when you make a new phprenderer rather than using the configured one

I had the lesser of the reason apparently: I was using $this->url() in my layout. Because there was no route match--a 404 error--it was blowing up on all 404 errors.

<Bittarman> for all of those things, stop doing if (!$this->url() == $this->url('home') etc
<ezio> ummm when it's home my business partner wants the whole order changed so google can hit on a bunch of keyords
<Bittarman> instead, in the VIEW for home, set what you need.
<ezio> how would i set the second example where i'm trying to highlight the currently-being-used menu item
<Bittarman> so, in your layout, you just want echo $this->headTitle()->setSeparator(' - ')->setAutoEscape(false)
<Bittarman> ezio, use the placeholder view helper
<ezio> okay
<ezio> thanks Bittarman ... tearing my hair out is not fun when you're already losing so much of it :p
<Bittarman> <?= $this->placeholder('currently-being-used') ?>
<Bittarman> and in your view, <?php $this->placeholder('currently-being-used')->append('foo') ?>
<ezio> sense making a lot you are
于 2013-09-14T23:08:26.320 に答える