Client-side code shouldn't be embedded in server-side schema?
JulianKingman opened this issue · 4 comments
I'm using SRF with OnsenUI, and I'm having this issue: in the schema (Simple Schema) I use client-side components as "type" for the srf field (e.g. name: {type: String, srf: {type: TextInput}}
). This in turn causes problems as some of the client-side code in OnsenUI can't be executed on the server, which SRF tries to do, since SimpleSchema is isomorphic.
My TextInput
field, for example, depends on a script that starts with the following if statement:
if (!window.CustomEvent) {
But unfortunately window doesn't exist on the server.
What's the best approach to handle this?
For now, I edited my field type so instead of doing this:
import {Input} from 'react-onsenui'
I do this:
if(Meteor.isClient){
Ons = require('react-onsenui');
}
render() {
<Ons.Input/>
}````
Can you show me more code?
Sure!
Before:
//TextInput.jsx, way simplified
import React, {Component} from 'react';
import {Input} from 'react-onsenui';
//'react-onsenui' depends on 'onsenui', which has a script that calls the window object;
//This is where I get an error something like "ReferenceError: window is not defined"
export default class TextInput extends Component {
constructor(props) {
super(props);
this.type = props.type || 'text';
this.state = {value: props.value};
}
render(){
<Input value={this.state.value || ''} type={this.type}/>
}
}
//Schema.js, simplified for clarity
const Incidents = new Mongo.Collection("incidents");
import {SimpleSchema} from 'meteor/aldeed:simple-schema';
import TextInput from '../../ui/components/FormElements/TextInput.jsx';
let Schemas = {};
Schemas.Incidents = new SimpleSchema({
Title: {
type: String,
srf: {
type: TextInput
}
}
});
After:
//TextInput.jsx
import React, {Component} from 'react';
//check if it's the client, I'm using Meteor, so...
if(Meteor.isClient){
Ons = require('react-onsenui');
}
export default class TextInput extends Component {
constructor(props) {
super(props);
this.type = props.type || 'text';
this.state = {value: props.value};
}
render(){
<Ons.Input value={this.state.value || ''} type={this.type}/>
}
}
//Schema.js
const Incidents = new Mongo.Collection("incidents");
import {SimpleSchema} from 'meteor/aldeed:simple-schema';
import TextInput from '../../ui/components/FormElements/TextInput.jsx';
let Schemas = {};
Schemas.Incidents = new SimpleSchema({
Title: {
type: String,
srf: {
type: TextInput
}
}
});
Does that clarify things more?
Hm.. I think you are doing it the best way possible 😕