ryan Posted December 30, 2010 Share Posted December 30, 2010 ProcessWire provides a 404 page that you can modify and customize like any other (and you'll see it in your Page List). ProcessWire will automatically display that 404 page when someone attempts to access a non-existent URL. If one of your templates is configured to show a 404 page when the user doesn't have access to a page (in Templates > Template > Advanced Settings), then it'll show your 404 page in that instance as well. There may be instances where you want to trigger 404 pages on your own from your templates. To do this, use the following PHP snippet: throw new PageNotFoundException(); Once you do that, processing of your template will stop and ProcessWire will send a 404 header and display the default 404 page instead (thereby passing control to your 404 template). Please note: you should throw the PageNotFoundException before outputting any content in your template. Link to comment Share on other sites More sharing options...
Pete Posted March 30, 2013 Share Posted March 30, 2013 Just a couple of notes - firstly, for anyone reading into throwing 404s in ProcessWire the preferred (as in used more in code samples here) way of doing this now seems to be this: throw new Wire404Exception(); Also, I tried using an include file at the top of my template called global.inc that does some global bits and pieces and I noticed that it seems impossible to throw Wire404Exception in an included file - it amusingly throws an exception 2 Link to comment Share on other sites More sharing options...
ryan Posted March 31, 2013 Author Share Posted March 31, 2013 Also, I tried using an include file at the top of my template called global.inc that does some global bits and pieces and I noticed that it seems impossible to throw Wire404Exception in an included file - it amusingly throws an exception How do you duplicate that? I tried to duplicate but couldn't. Here's the test I ran in my /site/templates/home.php: <?php include("./test.inc"); Here is /site/templates/test.inc: <?php throw new Wire404Exception(); Result was the 404 page. Link to comment Share on other sites More sharing options...
Pete Posted March 31, 2013 Share Posted March 31, 2013 I can confirm that it works in your example, just not when I include it in head.inc - I get this error: 2013-03-31 17:47:32 guest http://www.mysite.co.uk/dev/http404/ Error: Exception: (in /home/mysite/public_html/dev/site/templates/head.inc line 2) It's peculiar I know since the filename should make no difference. I then renamed my default head.inc to test.inc and updated the code in the homepage template and it throws a 404, renamed it back to head.inc and changed the include in home.php and it logs the error message above again. Link to comment Share on other sites More sharing options...
ryan Posted April 1, 2013 Author Share Posted April 1, 2013 Actually filename would make a difference here. The template used by the 404 page also includes head.inc. So head.inc gets included twice. If there are any function definitions (that get defined twice) that could trigger an exception. Also if the 404 is getting thrown without some kind of if() statement to know when to throw it, then it would be an infinite loop as the homepage throws it, then the 404 page throws it, and on and on. Link to comment Share on other sites More sharing options...
Peter Falkenberg Brown Posted September 1, 2013 Share Posted September 1, 2013 Dear Ryan and All, What's the best way to set up PW so that any 'page not found' error will simply redirect the user to the home page? In PW, or in the .htaccess file? Yours, Peter Link to comment Share on other sites More sharing options...
Martijn Geerts Posted September 1, 2013 Share Posted September 1, 2013 put on 404 template: $("session")->redirect("/"); Link to comment Share on other sites More sharing options...
SiNNuT Posted September 1, 2013 Share Posted September 1, 2013 No need for double redirects i think, just define it in your site/config.php: $config->http404PageID = 27; This line is from wire/config.php. Setting it in site/config.php should override. Just replace '27' with the id of any page you desire. Untested and maybe i'm overlooking an obvious drawback but this should work. 3 1 Link to comment Share on other sites More sharing options...
ryan Posted September 5, 2013 Author Share Posted September 5, 2013 404 pages serve an important purpose from an SEO standpoint. So if this is a public facing site, I'd recommend maintaining a proper 404 page rather than just redirecting to or displaying the homepage. You could always have your 404 page link to your homepage or even meta redirect to it after a few seconds. 7 Link to comment Share on other sites More sharing options...
Peter Falkenberg Brown Posted September 20, 2013 Share Posted September 20, 2013 Thanks, Ryan. That sounds like a good idea. Peter Link to comment Share on other sites More sharing options...
alexm Posted February 17, 2015 Share Posted February 17, 2015 Hi Guys, Am using the delayed output approach to the template structure and when I try: throw new PageNotFoundException(); I get: Error: Exception: (in /path/to/files/_main.php line 58) #0 /path/to/files/wire/core/TemplateFile.php(170): require()#1 [internal function]: TemplateFile->___render()#2 /path/to/files/wire/core/Wire.php(389): call_user_func_array(Array, Array)#3 /path/to/files/wire/core/Wire.php(344): Wire->runHooks('render', Array)#4 /path/to/files/wire/modules/PageRender.module(356): Wire->__call('render', Array)#5 /path/to/files/wire/modules/PageRender.module(356): TemplateFile->render()#6 [internal function]: PageRender->___renderPage(Object(HookEvent))#7 /path/to/files/wire/core/Wire.php(389): call_user_func_array(Array, Array)#8 /path/to/files/wire/core/Wire.php(344): Wire->runHooks('renderPage', Array)#9 /home/ What have I done wrong? Any suggestions would be sweet. Thanks Link to comment Share on other sites More sharing options...
adrian Posted February 18, 2015 Share Posted February 18, 2015 As noted above by Pete (2nd post), what you are actually looking for now is: throw new Wire404Exception(); Does that work for you, or is there something else going on still? 3 Link to comment Share on other sites More sharing options...
alexm Posted February 18, 2015 Share Posted February 18, 2015 Adrian, thanks for that!! All sorted. Apologies on my part for the stupid oversight. Many thanks again! Link to comment Share on other sites More sharing options...
flydev Posted January 12, 2018 Share Posted January 12, 2018 I can't get the 404 working in a template or bootstrapped script : <?php namespace ProcessWire; include_once(__DIR__ . '/../index.php'); if(!$config->ajax || !$user->isGuest()) { throw new Wire404Exception(); } as @Pete already said, it amusingly throws an exception on my install. I am on PW 3.0.88 but was not working on 3.086 either. What I can check ? If it help, I have TemplateEngineFactory installed and I think its the main cause. I might have posted on the module's thread... Quote Fatal error: Uncaught ProcessWire\Wire404Exception in /www/sites/***/wwwroot/api/contact.php:14 Stack trace: #0 {main} thrown in /www/sites/***/wwwroot/api/contact.php on line 14 Link to comment Share on other sites More sharing options...
gmclelland Posted January 12, 2018 Share Posted January 12, 2018 @flydev - I have ran into the same issues with my sites that use TemplateEngineFactory with TWIG. I had to do the following: $session->redirect($pages->get($config->http404PageID)->httpurl()); throw new Wire404Exception(); Maybe you could post something in the TemplateEngineFactory topic? Maybe @Wanze would know of a fix? Link to comment Share on other sites More sharing options...
flydev Posted January 13, 2018 Share Posted January 13, 2018 Thanks you. it turns out that with TemplateEngineFactory it works - at least for me - in templates, the 404 is fired, but not in bootstrapped script ? It is your case ? And I ended up testing to throw a 404 from a bootstrapped script on two others websites which don't have TemplateEngineFactory and also on a fresh install and it doesn't work, I think we can dismiss the module. Link to comment Share on other sites More sharing options...
kixe Posted July 14, 2018 Share Posted July 14, 2018 Getting wrong header if 404 is triggered inside template file. Calling a not existing page http://example.org/not/existing/page the correct http status header is sent: 404 Page Not Found The following code inside the template file renders properly page with id=27 but sends header 200 OK instead of 404 throw new Wire404Exception(); Would like to see 404. Link to comment Share on other sites More sharing options...
Soma Posted July 14, 2018 Share Posted July 14, 2018 1 hour ago, kixe said: Getting wrong header if 404 is triggered inside template file. Calling a not existing page http://example.org/not/existing/page the correct http status header is sent: 404 Page Not Found The following code inside the template file renders properly page with id=27 but sends header 200 OK instead of 404 throw new Wire404Exception(); Would like to see 404. I can't reproduce this. It's status 404. Link to comment Share on other sites More sharing options...
kixe Posted July 15, 2018 Share Posted July 15, 2018 I have to correct myself. I missed a hook that triggered the 404. Everything is working as expected and as it should work. Link to comment Share on other sites More sharing options...
CalleRosa40 Posted March 16, 2022 Share Posted March 16, 2022 Hi everyone, I read the thread, however I still experience some strange behavior. I suspect it has to do with delayed output, but I don't get it. For certain cases (ie URL segments that shouldn't be accessible for guests) I need to manually throw a 404 exception in one of my templates. First I got a compile error about not being able to redeclare some function. I fixed that by replacing all includes in my (auto-prepended) _init.php with include_onces. Now my 404 page is displayed but incompletely. PHP gives me multiple warnings about undefined variables in _main.php – those variables that are defined in the files I include in _init.php. What's going on here? I'm sure there is a simple reason, I just can't figure it out. Any ideas? I'll be most grateful for any hint! Link to comment Share on other sites More sharing options...
Robin S Posted March 16, 2022 Share Posted March 16, 2022 9 hours ago, CalleRosa40 said: What's going on here? It's explained in this post: 10 hours ago, CalleRosa40 said: PHP gives me multiple warnings about undefined variables in _main.php – those variables that are defined in the files I include in _init.php. Try separating functions from declared variables. See how it is done in the core site-default profile: https://github.com/processwire/processwire/blob/d78276e2c265f6b70384a13eb4febd4811a1db77/site-default/templates/_init.php Put all your functions in a file that is pulled in with include_once. Declare your variables in _init.php. 1 1 Link to comment Share on other sites More sharing options...
CalleRosa40 Posted March 17, 2022 Share Posted March 17, 2022 Thank you, @Robin S. 11 hours ago, Robin S said: Put all your functions in a file that is pulled in with include_once. Declare your variables in _init.php. I'd say that is exactly what I did from the very beginning. Here's the the essential part of my _init.php (which is automatically prepended to all my template files): include_once('_func.php'); include_once('_header.php'); include_once('_sidebar.php'); include_once('_footer.php'); include_once('_buttons.php'); _func.php contains all of my functions. I pull in _header.php etc. to define the variables (holding HTML) which are then output in _main.php. I put the declarations into separate files for better overview (_init.php would get rather lengthy if I didn't). That is a vaild way to go, isn't it? However, when throwing the 404 exception in my template like this if($user->hasRole("abc") || $user->hasRole("xyz") || $user->isSuperuser()) { ... } else throw new Wire404Exception(); the 404 page is displayed but with PHP warnings about not finding my content variables (which are needed to put the 404 page together, for menus etc.). The included files seem to get loaded because I can call functions defined in _func.php in my template. However all variables defined in _header.php etc. get "lost" somehow. Why? Thanks again! Link to comment Share on other sites More sharing options...
aagd Posted March 17, 2022 Share Posted March 17, 2022 My uneducated guess: Maybe a namespace issue? Are all your files in `namespace ProcessWire`? Link to comment Share on other sites More sharing options...
CalleRosa40 Posted March 17, 2022 Share Posted March 17, 2022 Hi @aagd, Thought of that, too. All my templates are being auto-compiled, so that shouldn't be a problem. I also tried adding namespace spec manually to the files – didn't help. Thanks anyway. Link to comment Share on other sites More sharing options...
aagd Posted March 17, 2022 Share Posted March 17, 2022 Next guess: a variable scope issue like in Make variables in _init.php available inside functions in _func.php - General Support - ProcessWire Support Forums Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now