On 8/21/16 Aug 21 -7:49 PM, Elias Pipping wrote:
Dear Robert, dear list,
I’m happy to see the first changes to run-program in ASDF-3.1.7.7. I’m now working more pragmatically towards making others mergeable. As usual, the list can be viewed at
https://gitlab.common-lisp.net/asdf/asdf/merge_requests/3
As of right now, it looks like this:
8e4f7fd Add and use process-info class ec74b27 Add %if-on-lispworks?+ ba8c24e Bug fix: Exit code with LispWorks 7 a35fbe2 Bug fix: Store exit code with Allegro CL 104da21 Change :if-*-exists default to :supersede 4ef7409 Add and use not-implemented-error 6359a4b Add file-stream*-p c2d5de3 Add and use parameter-error. Reorganise errors. 7ae0bcf Fix warnings on ABCL, etc. fb3dd9a Add and use close-streams 4971606 Add %process-info-*put getters c7570da Tests: Cover %run-program and %wait-process-result 1f43e5d Do not pass unnecessary keywords to SBCL
Should we have another iteration on this, putting it into a topic branch and letting me test it on Windows, Mac, and Linux?
TBH, I have never used merge requests on gitlab or github (except as submitting them), so I don't know the workflow from the recipient side. My use of git is mostly limited to command-line.
best, r
Dear Elias,
I gave a cursory look at your PR curently culminating at https://gitlab.common-lisp.net/asdf/asdf/commit/f8068ef93f71908f3c7786c62e94...
1- Why do you (setf (fdefinition '%wait-process-result) #'wait-process-result) ? I can't find any mention of that symbol in quicklisp besides copies of asdf or uiop. I propose you kill that old symbol and rename the new one to whatever you prefer. wait-process or process-wait, without -result, would be nice. Though whether you use process as prefix or suffix, try to make it coherent in all function names.
2- Similarly, when deciding what to do with internals (or even externals), grep'ing the contents of quicklisp is good policy. Though regarding external symbol, even if no one in quicklisp uses it, it's good citizenship to go through a complete 2-year obsolescence cycle.
3- I find %if-on-lispworks7+ particularly ugly. I'd create a feature and add it in common-lisp.lisp. But I admit this is a weak preference.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org There are three types of people in the world; those who can count, and those who can't.
On Mon, Aug 22, 2016 at 12:34 PM, Robert Goldman rpgoldman@sift.net wrote:
On 8/21/16 Aug 21 -7:49 PM, Elias Pipping wrote:
Dear Robert, dear list,
I’m happy to see the first changes to run-program in ASDF-3.1.7.7. I’m now working more pragmatically towards making others mergeable. As usual, the list can be viewed at
https://gitlab.common-lisp.net/asdf/asdf/merge_requests/3
As of right now, it looks like this:
8e4f7fd Add and use process-info class ec74b27 Add %if-on-lispworks?+ ba8c24e Bug fix: Exit code with LispWorks 7 a35fbe2 Bug fix: Store exit code with Allegro CL 104da21 Change :if-*-exists default to :supersede 4ef7409 Add and use not-implemented-error 6359a4b Add file-stream*-p c2d5de3 Add and use parameter-error. Reorganise errors. 7ae0bcf Fix warnings on ABCL, etc. fb3dd9a Add and use close-streams 4971606 Add %process-info-*put getters c7570da Tests: Cover %run-program and %wait-process-result 1f43e5d Do not pass unnecessary keywords to SBCL
Should we have another iteration on this, putting it into a topic branch and letting me test it on Windows, Mac, and Linux?
TBH, I have never used merge requests on gitlab or github (except as submitting them), so I don't know the workflow from the recipient side. My use of git is mostly limited to command-line.
best, r
On 23 Aug 2016, at 04:23, Faré fahree@gmail.com wrote:
Dear Elias,
Dear Faré,
I gave a cursory look at your PR curently culminating at https://gitlab.common-lisp.net/asdf/asdf/commit/f8068ef93f71908f3c7786c62e94...
thanks!
1- Why do you (setf (fdefinition '%wait-process-result) #'wait-process-result) ? I can't find any mention of that symbol in quicklisp besides copies of asdf or uiop. I propose you kill that old symbol and rename the new one to whatever you prefer. wait-process or process-wait, without -result, would be nice. Though whether you use process as prefix or suffix, try to make it coherent in all function names.
Great, the fewer unnecessary names the better. I was wondering about the process prefix/suffix already. I found alive-p (vs. process-alive-p) and status (vs. process-status) too short and not self-explanatory. But then, I found process-close-streams too long (albeit not by a lot so maybe that’s actually a good name) and process-close confusing weird. So currently, I have, among the exported functions:
- process-alive-p - terminate-process - wait-process - close-streams
2- Similarly, when deciding what to do with internals (or even externals), grep'ing the contents of quicklisp is good policy. Though regarding external symbol, even if no one in quicklisp uses it, it's good citizenship to go through a complete 2-year obsolescence cycle.
The sources for every project on quicklisp? Is there a central repository that holds all of those, or a simple way to obtain them?
3- I find %if-on-lispworks7+ particularly ugly. I'd create a feature and add it in common-lisp.lisp. But I admit this is a weak preference.
Yes, I found it terribly ugly, too. I wasn’t aware that adding to *features* was something you’re allowed to do. I’ve now done that in
https://gitlab.common-lisp.net/asdf/asdf/commit/13df4e9364527dd5b9197012b1eb...
and the code has ended up looking quite a bit nicer again, in particular because with #+ instead of macros I don’t need to use find-symbol* and (declare (ignore)) will work.
I’ve also pushed a fix for the LispWorks 6 warning in
https://gitlab.common-lisp.net/asdf/asdf/commit/590952a8afc9ca57e0a9cc917105...
(thanks a lot to Robert for helping me debug that!).
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
Elias
: Faré
: Elias
2- Similarly, when deciding what to do with internals (or even externals), grep'ing the contents of quicklisp is good policy. Though regarding external symbol, even if no one in quicklisp uses it, it's good citizenship to go through a complete 2-year obsolescence cycle.
The sources for every project on quicklisp? Is there a central repository that holds all of those, or a simple way to obtain them?
My system ql-test https://gitlab.common-lisp.net/frideau/ql-test provides a few utility functions that might prove useful.
3- I find %if-on-lispworks7+ particularly ugly. I'd create a feature and add it in common-lisp.lisp. But I admit this is a weak preference.
Yes, I found it terribly ugly, too. I wasn’t aware that adding to *features* was something you’re allowed to do. I’ve now done that in
https://gitlab.common-lisp.net/asdf/asdf/commit/13df4e9364527dd5b9197012b1eb...
and the code has ended up looking quite a bit nicer again, in particular because with #+ instead of macros I don’t need to use find-symbol* and (declare (ignore)) will work.
Yes, it is allowed, but with a lot of parcimony. I frown upon random systems adding a feature to show they're present: that's bad practice from before the time when defsystem was universal. But in some cases (uiop/os, trivial-features, etc.), it's a way to provide a uniform interface to the underlying implementation, and is therefore justified.
I’ve also pushed a fix for the LispWorks 6 warning in
https://gitlab.common-lisp.net/asdf/asdf/commit/590952a8afc9ca57e0a9cc917105...
(thanks a lot to Robert for helping me debug that!).
Thanks to the two of you!
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
Yes, it's a good idea.
Sigh. I like to say that UIOP is a library that does literally nothing -- but the same nothing uniformly on 15 different implementations. And that's hard.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org The competitor to be feared is one who never bothers about you at all, but goes on making his own business better all the time. — Henry Ford
: Faré
: Elias
: Faré
2- Similarly, when deciding what to do with internals (or even externals), grep'ing the contents of quicklisp is good policy. Though regarding external symbol, even if no one in quicklisp uses it, it's good citizenship to go through a complete 2-year obsolescence cycle.
The sources for every project on quicklisp? Is there a central repository that holds all of those, or a simple way to obtain them?
My system ql-test https://gitlab.common-lisp.net/frideau/ql-test provides a few utility functions that might prove useful.
Thanks, that’s very useful indeed (thanks also for the README!)
Elias
On 8/23/16 Aug 23 -6:42 AM, Elias Pipping wrote:
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
I have a busy day today, but I will try to get it done.
I was thinking of having slots for:
- implementation - capability name - optional format control and format args that the programmer can use to provide additional information. E.g., for LW, say that it's for licensing reasons that the DELIVER capability is not available.
If this sounds reasonable, I'll put it in, and try to find places it should be used.
In an earlier email, Elias points out that there are related reasons why a function might have failed. I haven't had time to figure out whether these would call for additional condition classes.
R
On 23 Aug 2016, at 15:50, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -6:42 AM, Elias Pipping wrote:
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
I have a busy day today, but I will try to get it done.
I was thinking of having slots for:
- implementation
- capability name
- optional format control and format args that the programmer can use to
provide additional information. E.g., for LW, say that it's for licensing reasons that the DELIVER capability is not available.
If this sounds reasonable, I'll put it in, and try to find places it should be used.
In an earlier email, Elias points out that there are related reasons why a function might have failed. I haven't had time to figure out whether these would call for additional condition classes.
I was thinking: We’re trying to tell the user that what they’re doing does not work. Yes, the function does exist, you’re passing the right number of arguments and the right keywords but there’s a problem. The problem could be:
- Your lisp is very old or very new or nobody’s gotten around to looking into it, so even though your lisp might provide the necessary functionality, the wrapper hasn’t been made to cover it yet (that’s what the master branch currently uses (error “not implemented: ~S” #’function-name) for) - You’re passing a combination of parameters that is not supported on this lisp (that’s what the master branch currently uses (assert) for) - The function or combination of parameters you’re calling it with is affected by a known bug on your lisp that we cannot work around.
I was thinking that to the user, it does not make a difference which one of those three reasons a function call fails for, so we could use one condition for all three, and unsupported-functionality captures the concept pretty well.
The capability name would often have to be a rather long description than just a name this way, though, I’m afraid. I’m not sure if I understand the purpose behind the ‘implementation' key of the condition. If a feature is e.g. missing on lisp A and B, and you’re on lisp A, if would simply contain “A”? Or would it contain something like “A personal edition prior to version 2.5?”
Elias
On 8/23/16 Aug 23 -9:55 AM, Elias Pipping wrote:
On 23 Aug 2016, at 15:50, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -6:42 AM, Elias Pipping wrote:
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
I have a busy day today, but I will try to get it done.
I was thinking of having slots for:
- implementation
- capability name
- optional format control and format args that the programmer can use to
provide additional information. E.g., for LW, say that it's for licensing reasons that the DELIVER capability is not available.
If this sounds reasonable, I'll put it in, and try to find places it should be used.
In an earlier email, Elias points out that there are related reasons why a function might have failed. I haven't had time to figure out whether these would call for additional condition classes.
I was thinking: We’re trying to tell the user that what they’re doing does not work. Yes, the function does exist, you’re passing the right number of arguments and the right keywords but there’s a problem. The problem could be:
- Your lisp is very old or very new or nobody’s gotten around to looking into
it, so even though your lisp might provide the necessary functionality, the wrapper hasn’t been made to cover it yet (that’s what the master branch currently uses (error “not implemented: ~S” #’function-name) for)
- You’re passing a combination of parameters that is not supported on this
lisp (that’s what the master branch currently uses (assert) for)
- The function or combination of parameters you’re calling it with is
affected by a known bug on your lisp that we cannot work around.
I was thinking that to the user, it does not make a difference which one of those three reasons a function call fails for, so we could use one condition for all three, and unsupported-functionality captures the concept pretty well.
The capability name would often have to be a rather long description than just a name this way, though, I’m afraid. I’m not sure if I understand the purpose behind the ‘implementation' key of the condition. If a feature is e.g. missing on lisp A and B, and you’re on lisp A, if would simply contain “A”? Or would it contain something like “A personal edition prior to version 2.5?”
I was focusing on the implementation, and perhaps a version number, because I have mostly been thinking about how I would use this new error class in the tests. In particular, I was thinking of running the tests on all lisp implementations, and catching expected failures, rather than doing what we do now, which is disable the tests on platforms where we believe a function is not available.
If we were to run tests on all implementations/platforms, and catch expected errors, that would help us detect unexpected successes, when functionality that used to be broken starts to work.
Well, I have also been thinking about how nice it would be to have an understandable, standard error message for users who use an unsupported function by accident.
What about:
1. Capability -- what we were trying to do. 2. Implementation name -- string, or could be a keyword, if we were to add a list of keywords. 3. Optional version number 4. Optional platform (for, e.g., "this works on SBCL > 1.2, but not on Windows.") 5. Additional information (e.g., LW personal edition)
We could have a signal-unsupported-capability function that would auto-collect some of these slot values, to make this easier to use.
There's no tearing hurry for this, so I'm happy to have some more email cycles so that we can get it right.
Best, r
I'd rather keep it simple.
End-users don't care WHY something is failing, just THAT it is failing gracefully and that the reason for failure is known. Users (programmers) can use M-. from the error to find the source and comments. A short link to a suitable cliki.net page might help explain the proper investigation procedure.
I see no reason for some programmer-intensive protocol that leads to large image size increase for no clear benefit that M-. won't bring.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org Those "organizers" who confuse coordination and cooperation will have 100% coordination for 0% cooperation. All costs, no benefits.
On Thu, Aug 25, 2016 at 10:37 PM, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -9:55 AM, Elias Pipping wrote:
On 23 Aug 2016, at 15:50, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -6:42 AM, Elias Pipping wrote:
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
I have a busy day today, but I will try to get it done.
I was thinking of having slots for:
- implementation
- capability name
- optional format control and format args that the programmer can use to
provide additional information. E.g., for LW, say that it's for licensing reasons that the DELIVER capability is not available.
If this sounds reasonable, I'll put it in, and try to find places it should be used.
In an earlier email, Elias points out that there are related reasons why a function might have failed. I haven't had time to figure out whether these would call for additional condition classes.
I was thinking: We’re trying to tell the user that what they’re doing does not work. Yes, the function does exist, you’re passing the right number of arguments and the right keywords but there’s a problem. The problem could be:
- Your lisp is very old or very new or nobody’s gotten around to looking into
it, so even though your lisp might provide the necessary functionality, the wrapper hasn’t been made to cover it yet (that’s what the master branch currently uses (error “not implemented: ~S” #’function-name) for)
- You’re passing a combination of parameters that is not supported on this
lisp (that’s what the master branch currently uses (assert) for)
- The function or combination of parameters you’re calling it with is
affected by a known bug on your lisp that we cannot work around.
I was thinking that to the user, it does not make a difference which one of those three reasons a function call fails for, so we could use one condition for all three, and unsupported-functionality captures the concept pretty well.
The capability name would often have to be a rather long description than just a name this way, though, I’m afraid. I’m not sure if I understand the purpose behind the ‘implementation' key of the condition. If a feature is e.g. missing on lisp A and B, and you’re on lisp A, if would simply contain “A”? Or would it contain something like “A personal edition prior to version 2.5?”
I was focusing on the implementation, and perhaps a version number, because I have mostly been thinking about how I would use this new error class in the tests. In particular, I was thinking of running the tests on all lisp implementations, and catching expected failures, rather than doing what we do now, which is disable the tests on platforms where we believe a function is not available.
If we were to run tests on all implementations/platforms, and catch expected errors, that would help us detect unexpected successes, when functionality that used to be broken starts to work.
Well, I have also been thinking about how nice it would be to have an understandable, standard error message for users who use an unsupported function by accident.
What about:
- Capability -- what we were trying to do.
- Implementation name -- string, or could be a keyword, if we were to
add a list of keywords. 3. Optional version number 4. Optional platform (for, e.g., "this works on SBCL > 1.2, but not on Windows.") 5. Additional information (e.g., LW personal edition)
We could have a signal-unsupported-capability function that would auto-collect some of these slot values, to make this easier to use.
There's no tearing hurry for this, so I'm happy to have some more email cycles so that we can get it right.
Best, r
You are ignoring my proclaimed purpose of improving the testing of ASDF.
Sent from my iPhone
On Aug 25, 2016, at 22:21, Faré fahree@gmail.com wrote:
I'd rather keep it simple.
End-users don't care WHY something is failing, just THAT it is failing gracefully and that the reason for failure is known. Users (programmers) can use M-. from the error to find the source and comments. A short link to a suitable cliki.net page might help explain the proper investigation procedure.
I see no reason for some programmer-intensive protocol that leads to large image size increase for no clear benefit that M-. won't bring.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org Those "organizers" who confuse coordination and cooperation will have 100% coordination for 0% cooperation. All costs, no benefits.
On Thu, Aug 25, 2016 at 10:37 PM, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -9:55 AM, Elias Pipping wrote:
On 23 Aug 2016, at 15:50, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -6:42 AM, Elias Pipping wrote:
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
I have a busy day today, but I will try to get it done.
I was thinking of having slots for:
- implementation
- capability name
- optional format control and format args that the programmer can use to
provide additional information. E.g., for LW, say that it's for licensing reasons that the DELIVER capability is not available.
If this sounds reasonable, I'll put it in, and try to find places it should be used.
In an earlier email, Elias points out that there are related reasons why a function might have failed. I haven't had time to figure out whether these would call for additional condition classes.
I was thinking: We’re trying to tell the user that what they’re doing does not work. Yes, the function does exist, you’re passing the right number of arguments and the right keywords but there’s a problem. The problem could be:
- Your lisp is very old or very new or nobody’s gotten around to looking into
it, so even though your lisp might provide the necessary functionality, the wrapper hasn’t been made to cover it yet (that’s what the master branch currently uses (error “not implemented: ~S” #’function-name) for)
- You’re passing a combination of parameters that is not supported on this
lisp (that’s what the master branch currently uses (assert) for)
- The function or combination of parameters you’re calling it with is
affected by a known bug on your lisp that we cannot work around.
I was thinking that to the user, it does not make a difference which one of those three reasons a function call fails for, so we could use one condition for all three, and unsupported-functionality captures the concept pretty well.
The capability name would often have to be a rather long description than just a name this way, though, I’m afraid. I’m not sure if I understand the purpose behind the ‘implementation' key of the condition. If a feature is e.g. missing on lisp A and B, and you’re on lisp A, if would simply contain “A”? Or would it contain something like “A personal edition prior to version 2.5?”
I was focusing on the implementation, and perhaps a version number, because I have mostly been thinking about how I would use this new error class in the tests. In particular, I was thinking of running the tests on all lisp implementations, and catching expected failures, rather than doing what we do now, which is disable the tests on platforms where we believe a function is not available.
If we were to run tests on all implementations/platforms, and catch expected errors, that would help us detect unexpected successes, when functionality that used to be broken starts to work.
Well, I have also been thinking about how nice it would be to have an understandable, standard error message for users who use an unsupported function by accident.
What about:
- Capability -- what we were trying to do.
- Implementation name -- string, or could be a keyword, if we were to
add a list of keywords. 3. Optional version number 4. Optional platform (for, e.g., "this works on SBCL > 1.2, but not on Windows.") 5. Additional information (e.g., LW personal edition)
We could have a signal-unsupported-capability function that would auto-collect some of these slot values, to make this easier to use.
There's no tearing hurry for this, so I'm happy to have some more email cycles so that we can get it right.
Best, r
With all due respect, a few minutes ago you were saying I shouldn't expect to have the source code, in response to my desire to restore some of the source-finding functionality of load truename, but in this message you are telling me it's enough to have simple error objects because everybody has meta-dot to fall back upon.
So now I find myself arguing for the position you articulated in your last response! With respect to ASDF ( and explicitly as opposed to the case of my DSL, which happens to simply not work if the source code is not present), we know that programmers often have bundled copies of ASDF, provided by vendors without source, and so meta dot does not work.
Best, R
Sent from my iPhone
On Aug 25, 2016, at 22:21, Faré fahree@gmail.com wrote:
I'd rather keep it simple.
End-users don't care WHY something is failing, just THAT it is failing gracefully and that the reason for failure is known. Users (programmers) can use M-. from the error to find the source and comments. A short link to a suitable cliki.net page might help explain the proper investigation procedure.
I see no reason for some programmer-intensive protocol that leads to large image size increase for no clear benefit that M-. won't bring.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org Those "organizers" who confuse coordination and cooperation will have 100% coordination for 0% cooperation. All costs, no benefits.
On Thu, Aug 25, 2016 at 10:37 PM, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -9:55 AM, Elias Pipping wrote:
On 23 Aug 2016, at 15:50, Robert Goldman rpgoldman@sift.net wrote:
On 8/23/16 Aug 23 -6:42 AM, Elias Pipping wrote:
If we can agree on Robert’s unsupported-functionality error class, I’ll work that into the merge request, too.
I have a busy day today, but I will try to get it done.
I was thinking of having slots for:
- implementation
- capability name
- optional format control and format args that the programmer can use to
provide additional information. E.g., for LW, say that it's for licensing reasons that the DELIVER capability is not available.
If this sounds reasonable, I'll put it in, and try to find places it should be used.
In an earlier email, Elias points out that there are related reasons why a function might have failed. I haven't had time to figure out whether these would call for additional condition classes.
I was thinking: We’re trying to tell the user that what they’re doing does not work. Yes, the function does exist, you’re passing the right number of arguments and the right keywords but there’s a problem. The problem could be:
- Your lisp is very old or very new or nobody’s gotten around to looking into
it, so even though your lisp might provide the necessary functionality, the wrapper hasn’t been made to cover it yet (that’s what the master branch currently uses (error “not implemented: ~S” #’function-name) for)
- You’re passing a combination of parameters that is not supported on this
lisp (that’s what the master branch currently uses (assert) for)
- The function or combination of parameters you’re calling it with is
affected by a known bug on your lisp that we cannot work around.
I was thinking that to the user, it does not make a difference which one of those three reasons a function call fails for, so we could use one condition for all three, and unsupported-functionality captures the concept pretty well.
The capability name would often have to be a rather long description than just a name this way, though, I’m afraid. I’m not sure if I understand the purpose behind the ‘implementation' key of the condition. If a feature is e.g. missing on lisp A and B, and you’re on lisp A, if would simply contain “A”? Or would it contain something like “A personal edition prior to version 2.5?”
I was focusing on the implementation, and perhaps a version number, because I have mostly been thinking about how I would use this new error class in the tests. In particular, I was thinking of running the tests on all lisp implementations, and catching expected failures, rather than doing what we do now, which is disable the tests on platforms where we believe a function is not available.
If we were to run tests on all implementations/platforms, and catch expected errors, that would help us detect unexpected successes, when functionality that used to be broken starts to work.
Well, I have also been thinking about how nice it would be to have an understandable, standard error message for users who use an unsupported function by accident.
What about:
- Capability -- what we were trying to do.
- Implementation name -- string, or could be a keyword, if we were to
add a list of keywords. 3. Optional version number 4. Optional platform (for, e.g., "this works on SBCL > 1.2, but not on Windows.") 5. Additional information (e.g., LW personal edition)
We could have a signal-unsupported-capability function that would auto-collect some of these slot values, to make this easier to use.
There's no tearing hurry for this, so I'm happy to have some more email cycles so that we can get it right.
Best, r
On Fri, Aug 26, 2016 at 12:50 AM, Robert P. Goldman rpgoldman@sift.net wrote:
With all due respect, a few minutes ago you were saying I shouldn't expect to have the source code, in response to my desire to restore some of the source-finding functionality of load truename, but in this message you are telling me it's enough to have simple error objects because everybody has meta-dot to fall back upon.
You shouldn't have source code to *use* ASDF and understand THAT there is a bug and its nature. Hence, asserts not being OK to trigger in user-facing code. When additional run-program functionality is exposed, its asserts must be turned to conditional errors.
But you SHOULD have source code to *debug* ASDF. If you want to make your platform supported or discover why it isn't and what other platforms ARE supported, it's alright to require source code. And it is NOT alright to require programmers to duplicate the complex #+ patterns in source code into each and every error message. This way lies madness, as it will be hell to synchronize the source code with the in-source-code description of what precise implementations cause the code to fail.
Already, I had a bug matching a list of #+... with a #-(or ...) as the code evolved. If you believe you'll be able to provide for each error message a list of supported implementations with its minimal supported version number, you're sorely deluded.
What next? Have each error message include a matrix of which ASDF version supports which interface with which bug fix on which versions of which implementations? Including future versions? That's complete madness.
If you believe some power users care about such details, a more future-proof way, once again, is to include a short URL in the error message, and maintain your compatibility matrix there.
If you're only trying to report version numbers, there's implementation-identifier and asdf-version for that, and I don't see any reason to decorate some error messages with that and not others.
As for testing ASDF, we have asdf-test:with-expected-failure to keep things sane and #+ and leave-lisp to skip meaningless tests.
So now I find myself arguing for the position you articulated in your last response! With respect to ASDF ( and explicitly as opposed to the case of my DSL, which happens to simply not work if the source code is not present), we know that programmers often have bundled copies of ASDF, provided by vendors without source, and so meta dot does not work.
That should be OK to use ASDF. If they hit ASDF limitations or bugs and want to investigate, it is alright to require them to have ASDF sources. Indeed, we encourage people to install the latest (release) ASDF from source before they report a bug.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org Who released the most slaves? The one who spent his wealth buying them back? Or the capitalist who found a way to power mills with water? — Paul Claudel
Dear Faré,
On 26 Aug 2016, at 13:42, Faré fahree@gmail.com wrote:
I’ll chime in here because I believe this criticism is targeted at what I was proposing.
What next? Have each error message include a matrix of which ASDF version supports which interface with which bug fix on which versions of which implementations? Including future versions? That's complete madness.
If you believe some power users care about such details, a more future-proof way, once again, is to include a short URL in the error message, and maintain your compatibility matrix there.
If you're only trying to report version numbers, there's implementation-identifier and asdf-version for that, and I don't see any reason to decorate some error messages with that and not others.
As for testing ASDF, we have asdf-test:with-expected-failure to keep things sane and #+ and leave-lisp to skip meaningless tests.
I agree that my proposal would take us on a path towards a lot of effort (even though I think much of such effort could be automated, and my hope would be that through regression testing and bug reports to upstream, the list of x-does-not-work-on-y would decrease in size after a while again as we stop to support older versions). So here’s a rather radical counter-proposal:
For any free and open-source lisp that we seek to support, we only test the most recent release. If the feature is broken or unavailable on that version of that lisp or we simply haven’t gotten around to implementing the necessary glue code yet, we use #+that-lisp to indicate an error. In particular, we never even need to check the version of a lisp in asdf/uiop: If a user runs an different version of said lisp, it’s up to him or her to check if everything works as intended. With each release of asdf/uiop, we consequently need to record the list of most recent releases we tested with. As a bonus, we may or may not provide additional information in a feature matrix or as plain text online (e.g. in the gitlab wiki).
In particular, - If a bug is fixed in a lisp but the fix hasn’t made it into a release of that lisp yet, that info might go on the wiki, but the uiop/asdf code will remain as-is. We only touch it once there’s a release of that lisp (or put feature branches in place that we merge at the appropriate time). - If a bug occurs in an older version of a lisp, that information, too, might go on the wiki, but no effort will be made to work around the bug in asdf/uiop. Such bug reports would be consequently be closed as won’t-fix.
For any lisp that’s not free and open-source, we might want to take additional steps in order to support the previous major release; both for Allegro CL and LispWorks there are corresponding reader macros, so that resulting code should register rather low on the insanity scale, even with such additional support.
Elias
While I don't agree with you about how debuggable ASDF is, nor the how understandable are its failures, I DO agree with your feelings about keeping the error simple.
Most of the error components I was suggesting do not provide useful information to the user.
For the user, the important information is "why is this not supported?" and that has to do with static information the programmer should supply, rather than with information about what the current information is.
E.g., if an operation isn't supported on LispWorks 6.1, it doesn't help to tell the user that they have LW 6.1: it helps to tell them why it's not supported.
So what if I back off on making this more complicated, and we put in just a capability name (which may be helpful to match both for testing and for programming)?
That said, I would like feedback on how best to give feedback that's helpful to the user. E.g., if a features is not supported on LW 6.1 (but is supported on 7.0) or ABCL, then it's probably best for the ABCL user to get an error message that the feature is not supported on ABCL, but the LW user should get a message saying it's not supported on 6.1... if this is possible without too much effort.
What about the following candidate?
(with-upgradability () (define-condition unsupported-functionality (error) ((functionality :type string ;short name of functionality :initarg :functionality :reader functionality) (reason :initarg :reason :type (or string nil) ;format string :reader reason ) (reason-args :initarg :reason-args :type list :reader reason-args )) (:report (lambda (c s) (with-slots (functionality reason reason-args) c (if reason (format s "~a is not supported in this environment because ~?" functionality reason reason-args) (format s "~a is not supported in this environment." functionality)))))))
If this seems reasonable, I will start testing it by trying to put it in place of less specific calls to error.
One question I had was whether this should be a sub-class of SIMPLE-ERROR, and instead of REASON and REASON-ARGS, I should have used the standard FORMAT-CONTROL and FORMAT-ARGS. Those names are more informative about what the argument should be, but less informative about how the arguments will be used (since in this case they will be combined with the FUNCTIONALITY).
Thanks, r
On Fri, Aug 26, 2016 at 9:24 AM, Robert Goldman rpgoldman@sift.net wrote:
For the user, the important information is "why is this not supported?" and that has to do with static information the programmer should supply, rather than with information about what the current information is.
My contention is that the programmer cannot supply this information. Certainly not in a maintainable way.
Any accurate compatibility grid must be outside the source code.
As a programmer: You can't predict the bug in your code. You can't predict the bug in the implementation. You can't predict when the implementation will be fixed. You can't predict when ASDF will be fixed to support the implementation.
From the ASDF 2 principle "None shall have to input (and make up)
information he doesn't have", it is therefore NOT the responsibility of the programmer to tell the user which versions will or won't work.
And that goes not just for ASDF. Any user who expects to get this information from the program is a fool. If you believe there are too many such fools, include a URL to explain that to them -- and you'll be left with the bigger fools who still don't get it. If you're using a many-years-old version of LispWorks, something fails in ASDF, and you don't think of upgrading either LispWorks and/or ASDF, you're such a bigger fool.
So what if I back off on making this more complicated, and we put in just a capability name (which may be helpful to match both for testing and for programming)?
Yes, that's the one (and only) piece of information that needs to be included in the error message.
What about the following candidate?
(with-upgradability () (define-condition unsupported-functionality (error) ((functionality :type string ;short name of functionality :initarg :functionality :reader functionality) (reason :initarg :reason :type (or string nil) ;format string :reader reason ) (reason-args :initarg :reason-args :type list :reader reason-args )) (:report (lambda (c s) (with-slots (functionality reason reason-args) c (if reason (format s "~a is not supported in this environment because ~?" functionality reason reason-args) (format s "~a is not supported in this environment." functionality)))))))
If this seems reasonable, I will start testing it by trying to put it in place of less specific calls to error.
I would remove reason and reason-args. There's nothing useful the programmer can tell.
On the other hand, I would define a function that throws the error, because that's worth it:
(defun unsupported-functionality (functionality) (error 'unsupported-functionality :functionality functionality))
And yes, FORMAT-CONTROL and FORMAT-ARGUMENTS would be better names than REASON.
-#f
On 9/1/16 Sep 1 -7:40 PM, Faré wrote:
For the user, the important information is "why is this not supported?"
and that has to do with static information the programmer should supply, rather than with information about what the current information is.
My contention is that the programmer cannot supply this information. Certainly not in a maintainable way.
I'm sorry, I simply do not understand this claim.
Here is my counter-example, in your "handwriting," as it were:
#-(or abcl allegro clasp clisp clozure cmucl cormanlisp digitool ecl gcl genera lispworks mkcl sbcl scl xcl) (error "~S not implemented on ~S" 'delete-empty-directory (implementation-type))) ; genera
This seems to be exactly an example of what I'm claiming, and the error call you wrote could be replaced with
(error 'unsupported-functionality :functionality 'delete-empty-directory :reason "not supported on ~a" :reason-args (list (implementation-type)))
[Actually, I see that the comment here must be wrong, since it conflicts with the #- form....]
But I hope you get my drift.
Similarly, I have often written a first draft of a system using Allegro's EXCL.OSI filesystem utilities, and then replaced it with a portable version later.
(error 'unsupported-functionality :functionality <foo> :reason " relies on ACL-specific mktemp function.")
There are lots of systems out there, at least some of whose functionality relies on other implementation-specific information.
In that case yes, I as a programmer definitely DO know that it is not supported because I didn't bother to use other than Allegro-specific functions.
Best, r
On Thu, Sep 1, 2016 at 10:50 PM, Robert Goldman rpgoldman@sift.net wrote:
On 9/1/16 Sep 1 -7:40 PM, Faré wrote:
For the user, the important information is "why is this not supported?"
and that has to do with static information the programmer should supply, rather than with information about what the current information is.
My contention is that the programmer cannot supply this information. Certainly not in a maintainable way.
I'm sorry, I simply do not understand this claim.
Here is my counter-example, in your "handwriting," as it were:
#-(or abcl allegro clasp clisp clozure cmucl cormanlisp digitool ecl gcl genera lispworks mkcl sbcl scl xcl) (error "~S not implemented on ~S" 'delete-empty-directory (implementation-type))) ; genera
This seems to be exactly an example of what I'm claiming, and the error call you wrote could be replaced with
(error 'unsupported-functionality :functionality 'delete-empty-directory :reason "not supported on ~a" :reason-args (list (implementation-type)))
I was wrong then. It would always be "not supported on ~a", and yet it would always be wrong: one release later (if Genera is ever released again), the thing would be completely false and the message should have been "please upgrade your Genera installation, contact David K. Schmidt". Until DKS isn't the guy anymore, and then the message is wrong again.
Just the name of the unimplemented thing should be all.
Similarly, I have often written a first draft of a system using Allegro's EXCL.OSI filesystem utilities, and then replaced it with a portable version later.
(error 'unsupported-functionality :functionality <foo> :reason " relies on ACL-specific mktemp function.")
This is not a helpful or maintainable error message. There's no action the user can take based on the extra information in that message.
There are lots of systems out there, at least some of whose functionality relies on other implementation-specific information.
That's fine. Just throw an error on other implementations. Someone who wants to fix it will have to edit the source code, at which point you can have much more information in the code itself, including comments.
In that case yes, I as a programmer definitely DO know that it is not supported because I didn't bother to use other than Allegro-specific functions.
If you edit the source code, you don't need that message. If you don't edit the source code, you don't need that message. No one needs that message.
If you want, the generic message could explain that this version of ASDF doesn't support this functionality on this version of the implementation. Still both obvious to a programmer and not helpful.
—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org To those who ask "why would anyone want to write free software for free?", I answer: "why would anyone want to write a PhD thesis?" — Faré
On 26 Aug 2016, at 04:37, Robert Goldman rpgoldman@sift.net wrote:
Dear Robert,
I was focusing on the implementation, and perhaps a version number, because I have mostly been thinking about how I would use this new error class in the tests. In particular, I was thinking of running the tests on all lisp implementations, and catching expected failures, rather than doing what we do now, which is disable the tests on platforms where we believe a function is not available.
yes, I was hoping for that, too. It's what prompted me to suggest extending unsupported-functionality to cover the three types of expected errors I was seeing.
If we were to run tests on all implementations/platforms, and catch expected errors, that would help us detect unexpected successes, when functionality that used to be broken starts to work. Well, I have also been thinking about how nice it would be to have an understandable, standard error message for users who use an unsupported function by accident.
I agree. I think the transition from user to developer is smooth. With a descriptive error message, a person might be able to understand what the problem is right away (oftentimes, the solution will be that they’ll just have to a use a newer version of the lisp they’re on), he or she might be able to find somebody with the very same problem (and an explanation or solution) on his or her favourite search engine, etc.
What about:
- Capability -- what we were trying to do.
- Implementation name -- string, or could be a keyword, if we were to
add a list of keywords.
Like *implementation* from test/script-support.lisp?
- Optional version number
- Optional platform (for, e.g., "this works on SBCL > 1.2, but not on
Windows.") 5. Additional information (e.g., LW personal edition)
Indeed it seems like 'personal edition' doesn’t fit into (2) or (3) this way. (It would fit better into (2) than (3) if the keywords allowed for that, I think). Those five fields should suffice, though.
We could also just use (lisp-implementation-type) and (lisp-implementation-version) for (2) and (3) instead of coming up with a custom solution.
We could have a signal-unsupported-capability function that would auto-collect some of these slot values, to make this easier to use.
I’d like to avoid misleadingly precise error messages though (think "this feature is not implemented on some-lisp 19.3.2 running inside cygwin on 32-bit windows” which could be generated from automatically retrievable information) when we’ve simply not gotten around to implementing the function on some-lisp or windows at all. (the message would suggest that upgrading to version 20 might help which it would not).
There's no tearing hurry for this, so I'm happy to have some more email cycles so that we can get it right.
Actually, it’s now been the one thing that’s been keeping me from working on my run-program changes because a considerable part of the changes I already have adds or cleans up handling of errors. But it probably shouldn’t be. I’ll try to isolate the bug fixes better from the invasive changes and have the latter queue up after the unsupported-functionality proposal. Because you’re right, this shouldn’t be rushed, and at the same time, bug fixes shouldn’t have to wait.
Elias
PS: Obtaining printable version information for (2) is not difficult. Checking if the current version is more recent than another version will generally be hard to impossible, in contrast. We desperately need such checks, though, if we want to generate errors in a reliable fashion.