donnikitos / vite-plugin-php

Vite's speed and tooling to preprocess PHP-files!
https://www.npmjs.com/package/vite-plugin-php
MIT License
34 stars 0 forks source link

prevent injection of @vite/client script tag #27

Closed krei-se closed 1 month ago

krei-se commented 1 month ago

i try to export to json from a php file and get an @vite/client script tag on top of the returned php page.

I know i can somehow inject a middleware to prevent this, but i would love to know if there is an easier way.

On another note: It's unclear a bit to me how you include partials in your starter repo. There are php files directly in /partials like nav.php included, but folder/*/.php would only include php files in subdirectories for me.

Currently i help myself with a mishmash of vite-plugin-static-copy and render on my webserver, but i would love php integration on my dev side.

I will look into these issues on my own but maybe those issues are bothering someone else too :)

donnikitos commented 1 month ago

Hi @krei-se,

first of all, thanks for the coffee and the issue submission :)

For the compilation partials are processed via Vite in the config file: image So all PHP-files in the partials/ subdirectory will be transpiled. In PHP you need to include them as usual with an include() statement: image

For this to work the index.php is adding the root of the project to the include_path: image


Regarding the JSON output - I understand the error, that you are getting, but I do not fully understand, how to reproduce it. Do you have some example code? This error usually happens, if the router can not find the correct file. Have you tried adding the file, or file extension to the rewriteUrl() routing configuration?

krei-se commented 1 month ago

I'm making progress after breaking it even more.

                        usePHP({
                                entry: ['index.php', 'php/*.php', 'php/**/*.php']
                        }),

this works somewhat, but the issue is, that i cannot include with just relative paths from any php file that is not in the root of the project. f.e. if you have a file under php, FILE / DIR will get the router.php and you always need to full include path for anything under /php/include/functions or similar. a file under /php can not include "subdir/another.php".

But for now that's just the way it is and it works somewhat with full paths! :)

Edit: I will reread the routing-table, but as far as i understand you can not know you are in about/details.php from inside the script and include sth. like /about/includes/function.php by a relative path from details.php

On the other issue: I use php for backend processing of stuff i don't want in any .ts files and want to have a php script send json:

<?php

$data = "Test.JSON";
header('Content-Type: application/json; charset=utf-8');
echo json_encode($data);

?>

saved under /php/json.php and defined as an entry point gets as output:

<script type="module" src="/@vite/client"></script>
 "Test.JSON" 
donnikitos commented 1 month ago

Pretty strange behavior to be honest 🤔 Is your main entry file the index.php from the starter repo? Does your config allow you to set ini_set('include_path')?


BTW, you can simplify your entry config to:

                        usePHP({
                                entry: ['index.php', 'php/**/*.php']
                        }),

This should cover all *.php files inside the php/ folder.


Alright, I see what the problem with JSON is: Vite tries to transpile it, as if it is HTML. That's not a big issue, a solution could be to read the response headers of the PHP server and determine what content type it is. If it's not text/html -> don't put it in the transpilation pipeline.

I can tackle that issue somewhere to the end of the week, stay tuned :)

krei-se commented 1 month ago

You are totally correct - only the /php/*/.php is needed!

i can set the include_path - but DIR will always be the location of router.php in node_modules/vite-plugin-php/dist so you can never have an include like ../db.php to include a file one folder above or hack together a solution that uses DIR from the file you want to include from.

5:54:08 AM [vite] page reload .php-tmp/main.php
index.mjs:6950
5:54:08 AM [vite] page reload .php-tmp/php/register.php
index.mjs:6950
5:54:08 AM [vite] page reload .php-tmp/php/include/db.php
index.mjs:6950
5:54:08 AM [vite] page reload .php-tmp/php/include/login.php
index.mjs:6950
5:54:08 AM [vite] page reload .php-tmp/php/include/functions/databasefunctions.php <-- trying to include('../db.php') here fails but will always work on any local / remote php installation / apache server.
index.mjs:6950
5:54:08 AM [vite] page reload .php-tmp/php/include/functions/logfunctions.php <-- working around this by using ini_set('include_path', ini_get('include_path') . PATH_SEPARATOR . __DIR__) will not work as __DIR__ is not ending in /include/functions but the dist-folder
index.mjs:6950
5:54:08 AM [vite] page reload .php-tmp/php/include/functions/wordfunctions.php

(made up names, don't laugh about my filenaming!!)

for now i just set include path from the ROOT that is in /dist and that's fine, but as you might guess, most coders coming from php expect their codebase to work somewhat similar to a simple host local / remote on an apache-server and i think making sure they get an easy same working environment will massively boost adoption rate of your plugin (which is great!).

Same for the header-issue, i think this script part is needed for hot module reloading, but i expect most migrators not knowing much about the vite middle-ware structure you deploy to have php working. An OOTB workaround and/or documentation how configserver / middleware works in vite and how your plugin is using it would greatly improve adoption.

donnikitos commented 1 month ago

@krei-se I understood your problem and have created a separate ticket for that, since that is a whole other thing to tackle 🤔

In the mean time you could import your files as if everything is project root based:

// /php/include/functions/databasefunctions.php

include('php/include/db.php');
krei-se commented 1 month ago

Thanks so much! I'm totally fine with this solution as i'm on a new project and this does not bug me that much. I can relate to the pain trying to make it work anyhow so im still impressed i can have a dev-setup like this!

Parsing xml from fetched .php output is fine and works around the script-issue for now but it will break any legacy software someone is trying to modernize.

This is more about having it adopted more easily to other devs. I tried nodejs for backend or vite/typescript for simple webpages and i cannot understand why people would replace a mature ecosystem like PHP.

Expect more debugging from me though as i will use this for a while :D

All the best!