
Nope. My mistake, this new code is adding different features.
On Wed, Jun 15, 2011 at 4:02 PM, Michael Litchard
I took a look at hello-forms.hs and this was my clue myForm = fixType $ runFormGet $ renderDivs $ pure (,,,,,,) <*> areq boolField "Bool field" Nothing <*> aopt boolField "Opt bool field" Nothing <*> areq textField "Text field" Nothing <*> areq (selectField fruits) "Select field" Nothing <*> aopt (selectField fruits) "Opt select field" Nothing <*> aopt intField "Opt int field" Nothing <*> aopt (radioField fruits) "Opt radio" Nothing
The aopt and areq look new. As far as I can tell, this looks like it should do what I needed. I'm eager to try it out.
On Wed, Jun 15, 2011 at 3:59 PM, David McBride
wrote: I haven't finished. I was making the changes he suggested, but found a problem. I sent him a question but he's probably a busy guy.
I don't see the changes in his github page, where are you getting this from? If you have found them, it is just a matter of taking the package, cabal configure, cabal install and then it should be available for all your coding needs.
On Wed, Jun 15, 2011 at 6:40 PM, Michael Litchard
wrote: David, I checked-out yesod-forms from the repository and see that you've made the changes. Thank you once again. My follow-up question is for anyone who cares to answer. How do I swap the new yesod-forms and the old one from 0.2.0? I don't want to hose my system. This is new ground for me.
On Tue, Jun 14, 2011 at 10:56 AM, Michael Litchard
wrote: Oh sweet! Thanks!
On Tue, Jun 14, 2011 at 9:43 AM, David McBride
wrote: I think I'll give it a shot. Fun problem and something I'll definitely need eventually. I'll try and get you a pull request tonight if all goes well.
On Tue, Jun 14, 2011 at 11:40 AM, Michael Snoyman
wrote: Hi David,
Thank you for the analysis, you're absolutely correct that this is a shortcoming in the API of yesod-form as it stands. I had an idea for a possibly simple modification to fix the situation: change fieldParse to
[Text] -> Either msg (Maybe a)
We don't really want to support returning singles or doubles from the same Field; a multiSelectField will automatically make the "a" variable a list. Said another way, the types should be:
selectField :: [(Text, a)] -> Field xml msg a multiSelectField :: [(Text, a)] -> Field xml msg [a]
Another related change: we don't really need to separate out fieldRender from fieldView I believe. Instead, we can have fieldView be:
fieldView :: Text -- ^ ID -> Text -- ^ name -> a -- currently, this is another Text -> Bool -- ^ required? -> xml
I'm willing to test out these changes myself, but wanted to (1) get input from you and (2) see if you or anyone else wanted to take a crack at it.
Michael
On Tue, Jun 14, 2011 at 4:25 PM, David McBride
wrote: > I gave a shot at this last night,and didn't quite pull it off. But I > got pretty far and I'd rather you have my work than try it from > scratch. > > The first method won't work because the Field type is used in > validating the get parameters in the mhelper function in > yesod.form.functions. That means that you have to have a unified type > for field that can do everything. Maybe there is a more succinct way > with classes, but I just couldn't think of an elegant way to do it > that way. > > So what I tried to do was make the fieldParser callback into its own type: > > newtype FieldParser msg a = FieldParser (Either > (Maybe Text -> Either msg (Maybe a)) > (Maybe [Text] -> Either msg (Maybe [a]))) > > That means a field parser can either take one text and return one > item, or it takes a list and returns a list of items. > > Then I went through Yesod.Form.Fields and changed about 12 or 15 references of > { fieldParse = blank $ \s -> > to > { fieldParse = FieldParser . Left $ blank $ \s -> > > Cool, now when you write your multipleSelectField, you'll set the fieldParser to > FieldParser . Right $ etc... > > The very last thing you have to do to fix this is the mhelper > function, which is where I lost steam. Right now it looks up the name > of the field in the get/post params that were passed in, and then > hands the value to fieldParse. What it needs to do is check to see > whether Field Parser is left or right, and then pass in the params > slightly differently depending on which it is. I don't know how the > parameters will end up getting passed into askParams though. Right > now askParams returns a list of names to value pairs, so hopefully you > will end up with a list of multiple entries for the name of your mutli > select and a different value for each entry, which you need to filter > out and collect into a single list and then run the fieldParser on it. > > Hopefully that is not too bad. > > > On Tue, Jun 14, 2011 at 4:30 AM, Michael Litchard wrote: >> Well I will try the easier way first, and having accomplished that I >> will look into doing it the better way. If people can call dibs, I'd >> like to. >> >> On Mon, Jun 13, 2011 at 9:47 PM, David McBride wrote: >>> After looking at the source, you should be aware that >>> >>> 1) yesod-form has been updated to 2.0, >>> 2) it is a lot easier to understand than 1.x was. >>> >>> The main obstacle I see is that the library uses the Field datatype, >>> that has a fieldParse method of Maybe Text -> Either msg (Maybe a). >>> The problem with that is that a multiple select box should require >>> [Text] or perhaps Maybe [Text] rather than Maybe Text. It is making >>> the assumption that there can only be one piece of data per field, >>> which holds for everything except multiple selects and multiple radio >>> buttons. >>> >>> So looking at this, it looks like you'd have to add another field type >>> "FieldMulti" to Yesod/Form/Types.hs, which allows for multiple values. >>> Then add a new version of selectFieldHelper that accepts fieldMultis >>> instead of fields, and then it is trivial to change selectField to be >>> a multi field. >>> >>> Alternatively you could change Field to accept either single or >>> multiple values and change its use everywhere else, which is probably >>> the better answer, but more involved. >>> >>> I don't know if this is the best way to go about it, but it seems like >>> it should work. >>> >>> On Mon, Jun 13, 2011 at 8:11 PM, Michael Litchard wrote: >>>> Thank you David. I'm trying to figure out step-by-step, exactly how >>>> selectFields binds field values. One thing I'm having trouble with is >>>> visualizing return values. >>>> Beginning with askParams. >>>> >>>> askParams :: Monad m => StateT Ints (ReaderT Env m) Env >>>> askParams = lift askenv <- askParams >>>> >>>> >>>> Here's the example from selectFields >>>> env <- askParams >>>> later on env is used in with the lookup function >>>> >>>> let res = case lookup name env of >>>> seeing as lookup is checking for value of type a in a [(a,b)] >>>> and given the type of askParams >>>> I have no idea what is going on here. I don't see a [(a,b)] in >>>> askParams :: Monad m => StateT Ints (ReaderT Env m) Env. >>>> >>>> So if someone could answer how env <- askParams yields a [(a,b)] for >>>> lookup to use as input, I would appreciate it. >>>> >>>> >>>> On Mon, Jun 13, 2011 at 2:54 PM, David McBride wrote: >>>>> The read function is sort of the opposite of the show function. Take >>>>> a string, give me a value. reads is like read, however it has some >>>>> traits that read doesn't have. >>>>> >>>>> The problem with read is that if you go: read "asdf" :: Int, it will >>>>> die with an exception, and that is something you don't want in a web >>>>> app. Also it doesn't tell you what the rest of the string is, so you >>>>> have no real way of finding out what was left of the string after the >>>>> part you wanted to parse. >>>>> >>>>> So there is the reads function that returns [(a,String)] which is a >>>>> list of pairs of the answer a, and the rest of the string String. As >>>>> a bonus, it returns a list so if it can't parse the string you pass >>>>> it, then it just returns an empty list. Why didn't it use Maybe you >>>>> ask? I bet it probably has to do with the function being one of the >>>>> first functions ever written for haskell, long before Maybe existed. >>>>> >>>>> So all it is there is unpack this bytestring into a string, then parse >>>>> it into a value, and please don't blow up if the input is invalid. >>>>> >>>>> On Mon, Jun 13, 2011 at 5:28 PM, Michael Litchard wrote: >>>>>> I was a bit hasty. I can render a multi-select field easily enough. >>>>>> However, I'm having difficulty following how selectField makes a value >>>>>> from the select field accessible from the handler code calling >>>>>> selectField. Once I figure that out, I can modify multiSelectField >>>>>> accordingly. >>>>>> >>>>>> The goal here being to modify selectField so that a list of field >>>>>> values can be bound . >>>>>> >>>>>> Here's what I have so far: >>>>>> multiSelectField is thus far identical in every way to selectField >>>>>> save for the following change in the Hamlet part. >>>>>> >>>>>> <select multiple="#{theId}" id="#{theId}" name="#{name}"> >>>>>> >>>>>> My thinking was that the value bound to multiple was arbitary, and I'd >>>>>> use theId until I figured out something that made more sense. >>>>>> >>>>>> Here's where I am focusing my efforts next >>>>>> >>>>>> http://hpaste.org/47774 >>>>>> >>>>>> Specifically >>>>>> (x', _):_ -> >>>>>> case lookup x' pairs' of >>>>>> Nothing -> FormFailure ["Invalid entry"] >>>>>> Just (y, _) -> FormSuccess y >>>>>> I'm thinking this is where selectField binds a value from the select >>>>>> field form. I'm confused by the (x',_):_. At first I thought it meant >>>>>> that just the first pair in a list of pairs is pattern matched >>>>>> against, and the rest discarded. But then I ask myself where the list >>>>>> is coming from. In a select field there would only be one pair, not a >>>>>> list of them. Here's where I get confused. Because if this is not >>>>>> where the values of the select field get bound, I don't know where >>>>>> it's happening. >>>>>> >>>>>> Is my confusion clear enough such that I could get some clarifying >>>>>> feedback? If not, what is unclear? >>>>>> >>>>>> On Sat, Jun 11, 2011 at 11:03 AM, Michael Snoyman wrote: >>>>>>> The best way for code contributions in general is to submit a pull >>>>>>> request on Github. If that's a problem, sending a patch via email >>>>>>> works as well (either directly to me or to web-devel). >>>>>>> >>>>>>> Michael >>>>>>> >>>>>>> On Sat, Jun 11, 2011 at 1:14 AM, Michael Litchard wrote: >>>>>>>> Hey! I just added multiSelectField to the Forms library. I'm only >>>>>>>> getting the first value selected, but I think that's because of how >>>>>>>> I'm using multiSelecrField. I'm going to try to change the client code >>>>>>>> to fix this. I'll let you know how it goes. when I get a >>>>>>>> maybeMultiSelectField added I'll show you what I have. What would be >>>>>>>> the best way to submit this? >>>>>>>> >>>>>>>> On Thu, Jun 9, 2011 at 10:05 PM, Michael Snoyman wrote: >>>>>>>>> Hi Michael, >>>>>>>>> >>>>>>>>> There's nothing jQuery or Javascript specific about a multi-select >>>>>>>>> field: it's just a normal select field with a "multiple" attribute. I >>>>>>>>> would recommend taking the selectField code from yesod-form and >>>>>>>>> modifying it to be multi-select. I'll likely do this myself >>>>>>>>> eventually, but it could be a good learning experience in Yesod (and a >>>>>>>>> great introduction to contributing to the framework if you're so >>>>>>>>> inclined). >>>>>>>>> >>>>>>>>> Michael >>>>>>>>> >>>>>>>>> On Thu, Jun 9, 2011 at 8:29 PM, Michael Litchard wrote: >>>>>>>>>> I'm trying to create a multiple select form, as illustrated on the following: >>>>>>>>>> http://api.jquery.com/selected-selector/ >>>>>>>>>> >>>>>>>>>> Here's the options I see possible: >>>>>>>>>> >>>>>>>>>> (1) Write a jQuery widget. >>>>>>>>>> (2) Use plain javascript via Julius >>>>>>>>>> (3) Use the low-level functions in Yesod.Form to write a widget >>>>>>>>>> (4) Use a pre-existing function that does what I need, but am not >>>>>>>>>> aware of this functionality >>>>>>>>>> >>>>>>>>>> (1) has appeal as it looks like something small I can contribute to >>>>>>>>>> the project. It will take me some extra time to figure out the >>>>>>>>>> details. But, I had a look at the other jQuery widgets and they seem >>>>>>>>>> to provide an approachable model to follow. >>>>>>>>>> >>>>>>>>>> (2) This looks like the most straight-forward approach. I'm just >>>>>>>>>> learning javascript so would have to figure out how to capture values >>>>>>>>>> in Haskell from the form. >>>>>>>>>> >>>>>>>>>> (3) This looks like the most difficult way. I don't think I know >>>>>>>>>> enough about the low-level functions in Yesod.Form to be able to >>>>>>>>>> accomplish this in a timely manner. >>>>>>>>>> >>>>>>>>>> (4) This is the best scenario. There's already a way to do this right >>>>>>>>>> now, and I just haven't identified it. If this is the case, I would >>>>>>>>>> appreciate being pointed in the right direction. >>>>>>>>>> >>>>>>>>>> Until informed otherwise, I'm evaluating options 1 and 2. All feedback >>>>>>>>>> welcomed. Thanks to all who made Yesod possible. >>>>>>>>>> >>>>>>>>>> _______________________________________________ >>>>>>>>>> Beginners mailing list >>>>>>>>>> Beginners@haskell.org >>>>>>>>>> http://www.haskell.org/mailman/listinfo/beginners >>>>>>>>>> >>>>>>>>> >>>>>>>> >>>>>>> >>>>>> >>>>>> _______________________________________________ >>>>>> Beginners mailing list >>>>>> Beginners@haskell.org >>>>>> http://www.haskell.org/mailman/listinfo/beginners >>>>>> >>>>> >>>>> _______________________________________________ >>>>> Beginners mailing list >>>>> Beginners@haskell.org >>>>> http://www.haskell.org/mailman/listinfo/beginners >>>>> >>>> >>> >>> _______________________________________________ >>> Beginners mailing list >>> Beginners@haskell.org >>> http://www.haskell.org/mailman/listinfo/beginners >>> >> > > _______________________________________________ > Beginners mailing list > Beginners@haskell.org > http://www.haskell.org/mailman/listinfo/beginners > _______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners