So because of the interlinking stuff I am doing, I was about to start on the specific interface for querying it. What I was thinking was that the function should be e.g. lookupLinkTarget :: TargetSpec -> MySite -> Destination
I have metadata files that I read with "readSource". Then fmap it over "sourceVal" to get just the value (discarding other fields). Would this not be better? So, "MySite LinkTargetData [XmlM]"
I figured why not put it in a ADT, and provide a simple sourceUrl function that gives the url to the rendered source. But it sounds like this URL in your case is something else ....
I'm writing an IRC log viewer using rib. And hit the abstracation ceiling of Source. Specifically I want to determine the output file name from the parsed structure (which contains the channel name).
It is basically impossible to customize buildHtml locally, because the Source constructor is not exported. Definitely a design smell that needs to be simplified, in the same manner as how I got rid of type classes.
Background:
I'm writing an IRC log viewer using rib. And hit the abstracation ceiling of Source. Specifically I want to determine the output file name from the parsed structure (which contains ...
The function hook thingy (i.e. readSource) is gone as well. No more needless passing-function-to-function indirections. Just call your parser directly in Action monad. (example in that link)
so what i mean is that i'd like to have my links look like entries/fp-glossary which would require the file to actally be written to entries/fp-glossary/index.html
I do that "index.html" trick when implementing IsRoute instance for my Route, and routeUrl automatically strips the "index.html" because it is redundant for URLs.
If you plan on using Route, you can start with a very basic implementation that has only one route:
classRouteawhereRoute_Whatever::PathRelFile->RouteXmlDocinstanceIsRouteRoutewhererouteFile=\caseRoute_Whateverfp->dropExtensionfp</>[relfile|index.html|]-- something like this
Then, (Route_Whatever fp, xmlDocForFp) will be isomorphic to your (Path, XmlDoc) type, and the second type ProcessedSource becomes redundant! Because you can just use the former, and call routeFile on it to get the HTML file path.
So because of the interlinking stuff I am doing, I was about to start on the specific interface for querying it. What I was thinking was that the function should be e.g.
lookupLinkTarget :: TargetSpec -> MySite -> Destination
so, I was about to buid a type for
MySite
what I was thinking of was something like:
data MySite = MySite LinkTargetData [Source XmlM]
HOWEVER, i notice that
Source
not only contains the "source" information but also targetwhich is semantically a bit separate IMO
(maybe I might want to have a source that has no direct desintation?)
just something I noticed, I will pobably end up using something besides
Source
for nowI have metadata files that I read with "readSource". Then fmap it over "sourceVal" to get just the value (discarding other fields). Would this not be better? So, "MySite LinkTargetData [XmlM]"
Actually no need for fmap,as readSource returns the underlying type directly
https://github.com/srid/website/blob/master/src/Main.hs#L63
oh sure
well the only thing is i'd like to also have the actual source filename as well
I suppose though that too could be optional
If you can show me how your
Source2
type would look in code (in the context of your project), I can evaluate it better.(I gtg soon; but feel free to put it here or on Github issue)
Na I think what you have is fine. I was mostly trying to say that it surprised me to see the dest filepath in the source data. But
I can get around it fine
and I can just ignore it too :)
Still interested in looking at what your code looks like, so let me know when it is done, I'll take a look at your repo.
In the early days I used a tuple
(FilePath, repr)
. Eg:("/foo/bar.md", <MMark doc>)
.And then some function that converted /foo/bar.md to /foo/bar.html for using in the HTML rendering step.
I figured why not put it in a ADT, and provide a simple
sourceUrl
function that gives the url to the rendered source. But it sounds like this URL in your case is something else ....Sure, will do
I'm writing an IRC log viewer using rib. And hit the abstracation ceiling of
Source
. Specifically I want to determine the output file name from the parsed structure (which contains the channel name).It is basically impossible to customize
buildHtml
locally, because theSource
constructor is not exported. Definitely a design smell that needs to be simplified, in the same manner as how I got rid of type classes.https://github.com/srid/rib/pull/94
I'm looking into the possibility of removing the
Source
type entirelyMinimum info we need is the parsed type, and the URL to it.
I think this URL is best constructed and defined manually by the user.
Actually .. removing
Source
makes the user code rather verbose and ugly. For now, think I'll keep it.Source
type is now entirely gone, replaced by a Route-based mechanism which looks pretty cleaner to me. See https://github.com/srid/rib-sample/commit/5a7f0c6d16efbd24065655b204c5ca11797439e6#diff-f8f3412da88cd4806f23d59fe59ebc3bR33The function hook thingy (i.e.
readSource
) is gone as well. No more needless passing-function-to-function indirections. Just call your parser directly in Action monad. (example in that link)I ended up making my own sort-of source type
that is just a tuple of like
(Path, XmlDoc)
Then there is a second type called ProcessedSource which includes the output destination
this solved the weirness
i like the new disign; basically it separates the process into:
Joel McCracken said:
This is isomorphic to Rib.Route's
(r a, a)
basically, FWIW.yea
totally is
i'm still tyring to figure out if i want to use the route
for now its easier to just not
that's a sensible approach. you can use it when you need it. i designed Rib.Route after figuring out based on my various static sites.
Joel McCracken said:
Also, this is why there is a
IsRoute
type class, to provide arouteFile
(whichrouteUrl
uses) that tells the output destination for a given route.I think it should work though
yeah
Joel McCracken said:
Yes, you can get away with your own Shake action, and use only two functions from Rib:
forEvery
(for step 1), andwriteFileCached
(after step 3)yep!
thats exactly what I am doing
and
forEvery
is basically a 3-line function that wraps Shake'sforP
I implemented it so my pjosts write to
entries/<post-name>/index.html
FYIoh thats what I was unsure about
it seemed like I couldn't easaily separate where I am acrtually writing a file to with the URL I use for links
?
so what i mean is that i'd like to have my links look like
entries/fp-glossary
which would require the file to actally be written toentries/fp-glossary/index.html
oh wait! I am wrong
looks like you explicitly programmed for that?
in routeUrl'
I do that "index.html" trick when implementing
IsRoute
instance for my Route, androuteUrl
automatically strips the "index.html" because it is redundant for URLs.what i mean is that if I have my file written to
entries/fp-glossary/index.html
, then the generated link will beentries/fp-glossary
nice
cool
ill probably factor to it then when I'm done fixing a few things
If you plan on using Route, you can start with a very basic implementation that has only one route:
And in future if you want to support non-xml docs, you can add another constructor, eg:
Route_NewStuff :: Path Rel File -> Route Pandoc
Working code for that index.html trick with Routes here: https://github.com/open-editions/open-editions.org/blob/930888f/Main.hs#L54-L69
Then,
(Route_Whatever fp, xmlDocForFp)
will be isomorphic to your(Path, XmlDoc)
type, and the second typeProcessedSource
becomes redundant! Because you can just use the former, and callrouteFile
on it to get the HTML file path.cool cool
... with the added benefit of being able to use
routeUrl
on that value