As I work my way through User Stories Applied and begin to write my own for an upcoming project, I keep coming back to Bill Wake's INVEST acronym. It helps me get in the right mindset. A good user story is independent, negotiable, valuable, estimatable, small, testable. If it can meet all those requirements, you've done a good job.
Stories that are independent make the whole development process easier. You don't have stories waiting for others to be completed so estimation of development time becomes more precise. Be creative, sometimes stories can be combined or defined in a way to decreases dependencies.
Stories help in the discovery and planning phase of a project. They facilitate the conversation between client and the development team. Remember to note high-level details and decisions that are made in these meetings.
Make sure each story provides value to either the purchaser or user of the product. This type of focus can help in the proritization of stories. Some clients are comfortable writing their own stories and this can provide good insight into their vision of the product.
If a story is not estimatable, it is usually too large or the development team lacks the domain or technical knowledge necessary for an estimation. A conversation with the client can increase domain understanding, while a developer can build technical understanding before estimation.
Small stories allow for the most accurate predictions. If they are too big or small, it is difficult to block out the correct about of development time. Combine or split stories to managable sizes. Stories can be split by user actions (separate create, edit, update stories).
A story is not complete until it can pass automated tests. Non-functional or overly subject requirements can lead to untestable conditions and should be avoided. As the code base evolves, you will continually use your tests to ensure old stories are not broken.