Testing SSR redirects

This commit is contained in:
Matthew Phillips 2022-03-08 17:01:34 -05:00
parent 049ab7dc96
commit 6b09b8e31b
11 changed files with 86 additions and 10 deletions

View file

@ -5,6 +5,10 @@ interface Product {
image: string;
}
interface User {
id: number;
}
//let origin: string;
const { mode } = import.meta.env;
const origin = mode === 'develepment' ? `http://localhost:3000` : `http://localhost:8085`;
@ -31,3 +35,10 @@ export async function getProduct(id: number): Promise<Product> {
return product;
});
}
export async function getUser(): Promise<User> {
return get<User>(`/api/user`, async response => {
const user: User = await response.json();
return user;
});
}

View file

@ -0,0 +1,22 @@
---
import { getUser } from '../api';
const isLoggedIn = false;
if(!isLoggedIn) {
return Astro.redirect('/');
}
// This person is logged in
const user = { name: 'test'} // await getUser();
---
<html>
<head>
<title>Logged in Page</title>
</head>
<body>
<h1>Logged in page</h1>
<h2>User: {user.name}</h2>
</body>
</html>

View file

@ -0,0 +1,7 @@
{
"compilerOptions": {
"lib": ["ES2015", "DOM"],
"module": "ES2022",
"types": ["astro/env"]
}
}

View file

@ -130,6 +130,8 @@ export async function staticBuild(opts: StaticBuildOptions) {
const topLevelImports = new Set([
// Any component that gets hydrated
// 'components/Counter.jsx'
// { 'components/Counter.jsx': 'counter.hash.js' }
...metadata.hydratedComponentPaths(),
// Client-only components
...metadata.clientOnlyComponentPaths(),

View file

@ -62,7 +62,7 @@ interface RenderOptions {
site?: string;
}
export async function render(opts: RenderOptions): Promise<string> {
export async function render(opts: RenderOptions): Promise<string | { location: string }> {
const { legacyBuild, links, logging, origin, markdownRender, mod, pathname, scripts, renderers, resolve, route, routeCache, site } = opts;
const [params, pageProps] = await getParamsAndProps({
@ -99,6 +99,10 @@ export async function render(opts: RenderOptions): Promise<string> {
let html = await renderToString(result, Component, pageProps, null);
if(typeof html === 'object') {
return html;
}
// handle final head injection if it hasn't happened already
if (html.indexOf("<!--astro:head:injected-->") == -1) {
html = await renderHead(result) + html;

View file

@ -116,7 +116,7 @@ export async function render(renderers: Renderer[], mod: ComponentInstance, ssrO
site: astroConfig.buildOptions.site,
});
if (route?.type === 'endpoint') {
if (route?.type === 'endpoint' || typeof content === 'object') {
return content;
}

View file

@ -44,6 +44,15 @@ export function createResult(args: CreateResultArgs): SSRResult {
params,
url,
},
redirect(path: string) {
// TOOD property response
return {
status: 301,
headers: {
Location: path
}
};
},
resolve(path: string) {
if (!legacyBuild) {
let extra = `This can be replaced with a dynamic import like so: await import("${path}")`;

View file

@ -420,16 +420,27 @@ export async function renderEndpoint(mod: EndpointHandler, params: any) {
}
// Calls a component and renders it into a string of HTML
export async function renderToString(result: SSRResult, componentFactory: AstroComponentFactory, props: any, children: any) {
export async function renderToString(result: SSRResult, componentFactory: AstroComponentFactory,
props: any, children: any): Promise<string | any> {
const Component = await componentFactory(result, props, children);
let template = await renderAstroComponent(Component);
// <!--astro:head--> injected by compiler
// Must be handled at the end of the rendering process
if (template.indexOf('<!--astro:head-->') > -1) {
template = template.replace('<!--astro:head-->', await renderHead(result));
if(Object.prototype.toString.call(Component) === '[object AstroComponent]') {
let template = await renderAstroComponent(Component);
// HACK
if(typeof template === 'object') {
return template;
}
// <!--astro:head--> injected by compiler
// Must be handled at the end of the rendering process
if (template.indexOf('<!--astro:head-->') > -1) {
template = template.replace('<!--astro:head-->', await renderHead(result));
}
return template;
} else {
return Component;
}
return template;
}
// Filter out duplicate elements in our set
@ -482,7 +493,8 @@ export async function renderAstroComponent(component: InstanceType<typeof AstroC
}
}
return unescapeHTML(await _render(template));
let html = await _render(template);
return unescapeHTML(html);
}
function componentIsHTMLElement(Component: unknown) {

View file

@ -0,0 +1,4 @@
<script type="module" hoist>
import "../scripts/used-nested";
</script>

View file

@ -0,0 +1,4 @@
---
import Component from '../../components/UsedNested.astro';
---
<Component/>

View file

@ -0,0 +1 @@
console.log("i am used from a component that's used from a nested page");