Fix first loads not working

This commit is contained in:
abias 2023-06-16 18:12:14 -04:00
parent 2a16c85ed0
commit 71336002e7
7 changed files with 73 additions and 80 deletions

View file

@ -17,9 +17,16 @@
"start": "yarn build:dev --watch"
},
"lint-staged": {
"*.{ts,tsx,js}": ["prettier --write", "eslint --fix"],
"*.{css, scss}": ["prettier --write"],
"package.json": ["sortpack"]
"*.{ts,tsx,js}": [
"prettier --write",
"eslint --fix"
],
"*.{css, scss}": [
"prettier --write"
],
"package.json": [
"sortpack"
]
},
"dependencies": {
"@babel/plugin-proposal-decorators": "^7.21.0",

View file

@ -17,13 +17,10 @@ import {
ILemmyConfig,
InitialFetchRequest,
IsoDataOptionalSite,
RouteData,
} from "../shared/interfaces";
import { routes } from "../shared/routes";
import {
FailedRequestState,
RequestState,
wrapClient,
} from "../shared/services/HttpService";
import { FailedRequestState, wrapClient } from "../shared/services/HttpService";
import {
ErrorPageData,
favIconPngUrl,
@ -140,7 +137,7 @@ server.get("/*", async (req, res) => {
// This bypasses errors, so that the client can hit the error on its own,
// in order to remove the jwt on the browser. Necessary for wrong jwts
let site: GetSiteResponse | undefined = undefined;
let routeData: Record<string, RequestState<any>> = {};
let routeData: RouteData = {};
let errorPageData: ErrorPageData | undefined = undefined;
let try_site = await client.getSite(getSiteForm);
if (try_site.state === "failed" && try_site.msg == "not_logged_in") {
@ -164,7 +161,7 @@ server.get("/*", async (req, res) => {
return res.redirect("/setup");
}
if (site) {
if (site && activeRoute?.fetchInitialData) {
const initialFetchReq: InitialFetchRequest = {
client,
auth,
@ -173,19 +170,7 @@ server.get("/*", async (req, res) => {
site,
};
if (activeRoute?.fetchInitialData) {
const routeDataKeysAndVals = await Promise.all(
Object.entries(activeRoute.fetchInitialData(initialFetchReq)).map(
async ([key, val]) => [key, await val]
)
);
routeData = routeDataKeysAndVals.reduce((acc, [key, val]) => {
acc[key] = val;
return acc;
}, {});
}
routeData = await activeRoute.fetchInitialData(initialFetchReq);
}
} else if (try_site.state === "failed") {
errorPageData = getErrorPageData(new Error(try_site.msg), site);

View file

@ -124,6 +124,39 @@ type HomeData = RouteDataResponse<{
trendingCommunitiesRes: ListCommunitiesResponse;
}>;
function getRss(listingType: ListingType) {
const { sort } = getHomeQueryParams();
const auth = myAuth();
let rss: string | undefined = undefined;
switch (listingType) {
case "All": {
rss = `/feeds/all.xml?sort=${sort}`;
break;
}
case "Local": {
rss = `/feeds/local.xml?sort=${sort}`;
break;
}
case "Subscribed": {
rss = auth ? `/feeds/front/${auth}.xml?sort=${sort}` : undefined;
break;
}
}
return (
rss && (
<>
<a href={rss} rel={relTags} title="RSS">
<Icon icon="rss" classes="text-muted small" />
</a>
<link rel="alternate" type="application/atom+xml" href={rss} />
</>
)
);
}
function getDataTypeFromQuery(type?: string): DataType {
return type ? DataType[type] : DataType.Post;
}
@ -235,11 +268,8 @@ export class Home extends Component<any, HomeState> {
// Only fetch the data if coming from another route
if (FirstLoadService.isFirstLoad) {
const {
trendingCommunitiesRes: trendingCommunitiesRes,
commentsRes: commentsRes,
postsRes: postsRes,
} = this.isoData.routeData;
const { trendingCommunitiesRes, commentsRes, postsRes } =
this.isoData.routeData;
this.state = {
...this.state,
@ -360,7 +390,7 @@ export class Home extends Component<any, HomeState> {
></div>
)}
<div className="d-block d-md-none">{this.mobileView}</div>
{this.posts()}
{this.posts}
</main>
<aside className="d-none d-md-block col-md-4">
{this.mySidebar}
@ -575,7 +605,7 @@ export class Home extends Component<any, HomeState> {
await this.fetchData();
}
posts() {
get posts() {
const { page } = getHomeQueryParams();
return (
@ -594,7 +624,7 @@ export class Home extends Component<any, HomeState> {
const siteRes = this.state.siteRes;
if (dataType === DataType.Post) {
switch (this.state.postsRes?.state) {
switch (this.state.postsRes.state) {
case "loading":
return (
<h5>
@ -700,44 +730,11 @@ export class Home extends Component<any, HomeState> {
<span className="mr-2">
<SortSelect sort={sort} onChange={this.handleSortChange} />
</span>
{this.getRss(listingType)}
{getRss(listingType)}
</div>
);
}
getRss(listingType: ListingType) {
const { sort } = getHomeQueryParams();
const auth = myAuth();
let rss: string | undefined = undefined;
switch (listingType) {
case "All": {
rss = `/feeds/all.xml?sort=${sort}`;
break;
}
case "Local": {
rss = `/feeds/local.xml?sort=${sort}`;
break;
}
case "Subscribed": {
rss = auth ? `/feeds/front/${auth}.xml?sort=${sort}` : undefined;
break;
}
}
return (
rss && (
<>
<a href={rss} rel={relTags} title="RSS">
<Icon icon="rss" classes="text-muted small" />
</a>
<link rel="alternate" type="application/atom+xml" href={rss} />
</>
)
);
}
async fetchTrendingCommunities() {
this.setState({ trendingCommunitiesRes: { state: "loading" } });
this.setState({

View file

@ -35,7 +35,7 @@ export interface CreatePostProps {
}
type CreatePostData = RouteDataResponse<{
communityResponse?: GetCommunityResponse;
communityResponse: GetCommunityResponse;
initialCommunitiesRes: ListCommunitiesResponse;
}>;
@ -244,6 +244,7 @@ export class CreatePost extends Component<
>): Promise<CreatePostData> {
const data: CreatePostData = {
initialCommunitiesRes: await fetchCommunitiesForOptions(client),
communityResponse: { state: "empty" },
};
if (communityId) {

View file

@ -6,16 +6,16 @@ import { ErrorPageData } from "./utils";
/**
* This contains serialized data, it needs to be deserialized before use.
*/
export interface IsoData<T extends Record<string, RequestState<any>> = any> {
export interface IsoData<T extends RouteData = any> {
path: string;
routeData: T;
site_res: GetSiteResponse;
errorPageData?: ErrorPageData;
}
export type IsoDataOptionalSite<
T extends Record<string, RequestState<any>> = any
> = Partial<IsoData<T>> &
export type IsoDataOptionalSite<T extends RouteData = any> = Partial<
IsoData<T>
> &
Pick<IsoData<T>, Exclude<keyof IsoData<T>, "site_res">>;
export interface ILemmyConfig {
@ -82,3 +82,5 @@ export interface CommentNodeI {
children: Array<CommentNodeI>;
depth: number;
}
export type RouteData = Record<string, RequestState<any>>;

View file

@ -21,13 +21,10 @@ import { CreatePost } from "./components/post/create-post";
import { Post } from "./components/post/post";
import { CreatePrivateMessage } from "./components/private_message/create-private-message";
import { Search } from "./components/search";
import { InitialFetchRequest } from "./interfaces";
import { RequestState } from "./services/HttpService";
import { InitialFetchRequest, RouteData } from "./interfaces";
interface IRoutePropsWithFetch<T extends Record<string, RequestState<any>>>
extends IRouteProps {
// TODO Make sure this one is good.
fetchInitialData?(req: InitialFetchRequest): T;
interface IRoutePropsWithFetch<T extends RouteData> extends IRouteProps {
fetchInitialData?(req: InitialFetchRequest): Promise<T>;
}
export const routes: IRoutePropsWithFetch<Record<string, any>>[] = [

View file

@ -43,7 +43,13 @@ import tippy from "tippy.js";
import Toastify from "toastify-js";
import { getHttpBase } from "./env";
import { i18n, languages } from "./i18next";
import { CommentNodeI, DataType, IsoData, VoteType } from "./interfaces";
import {
CommentNodeI,
DataType,
IsoData,
RouteData,
VoteType,
} from "./interfaces";
import { HttpService, UserService } from "./services";
import { RequestState } from "./services/HttpService";
@ -1166,9 +1172,7 @@ export function isBrowser() {
return typeof window !== "undefined";
}
export function setIsoData<T extends Record<string, RequestState<any>>>(
context: any
): IsoData<T> {
export function setIsoData<T extends RouteData>(context: any): IsoData<T> {
// If its the browser, you need to deserialize the data from the window
if (isBrowser()) {
return window.isoData;